/*
 * Copyright (C) 2014 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package android.app;

import android.animation.Animator;
import android.animation.AnimatorListenerAdapter;
import android.animation.ObjectAnimator;
import android.annotation.NonNull;
import android.app.SharedElementCallback.OnSharedElementsReadyListener;
import android.content.Intent;
import android.graphics.Color;
import android.graphics.Matrix;
import android.graphics.RectF;
import android.graphics.drawable.ColorDrawable;
import android.graphics.drawable.Drawable;
import android.os.Build.VERSION_CODES;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.os.ResultReceiver;
import android.transition.Transition;
import android.transition.TransitionListenerAdapter;
import android.transition.TransitionManager;
import android.view.View;
import android.view.ViewGroup;
import android.view.Window;

import com.android.internal.view.OneShotPreDrawListener;

import java.util.ArrayList;

/**
 * This ActivityTransitionCoordinator is created in ActivityOptions#makeSceneTransitionAnimation
 * to govern the exit of the Scene and the shared elements when calling an Activity as well as
 * the reentry of the Scene when coming back from the called Activity.
 *
 * @hide
 */
public class ExitTransitionCoordinator extends ActivityTransitionCoordinator {
    private static final String TAG = "ExitTransitionCoordinator";
    static long sMaxWaitMillis = 1000;

    private Bundle mSharedElementBundle;
    private boolean mExitNotified;
    private boolean mSharedElementNotified;
    private ExitTransitionCallbacks mExitCallbacks;
    private boolean mIsBackgroundReady;
    private boolean mIsCanceled;
    private Handler mHandler;
    private ObjectAnimator mBackgroundAnimator;
    private boolean mIsHidden;
    private Bundle mExitSharedElementBundle;
    private boolean mIsExitStarted;
    private boolean mSharedElementsHidden;

    public ExitTransitionCoordinator(ExitTransitionCallbacks exitCallbacks,
            Window window, SharedElementCallback listener, ArrayList<String> names,
            ArrayList<String> accepted, ArrayList<View> mapped, boolean isReturning) {
        super(window, names, listener, isReturning);
        viewsReady(mapSharedElements(accepted, mapped));
        stripOffscreenViews();
        mIsBackgroundReady = !isReturning;
        mExitCallbacks = exitCallbacks;
    }

    @Override
    protected void onReceiveResult(int resultCode, Bundle resultData) {
        switch (resultCode) {
            case MSG_SET_REMOTE_RECEIVER:
                stopCancel();
                mResultReceiver = resultData.getParcelable(KEY_REMOTE_RECEIVER, android.os.ResultReceiver.class);
                if (mIsCanceled) {
                    mResultReceiver.send(MSG_CANCEL, null);
                    mResultReceiver = null;
                } else {
                    notifyComplete();
                }
                break;
            case MSG_HIDE_SHARED_ELEMENTS:
                stopCancel();
                if (!mIsCanceled) {
                    hideSharedElements();
                }
                break;
            case MSG_START_EXIT_TRANSITION:
                mHandler.removeMessages(MSG_CANCEL);
                startExit();
                break;
            case MSG_SHARED_ELEMENT_DESTINATION:
                mExitSharedElementBundle = resultData;
                sharedElementExitBack();
                break;
            case MSG_CANCEL:
                mIsCanceled = true;
                finish();
                break;
        }
    }

    private void stopCancel() {
        if (mHandler != null) {
            mHandler.removeMessages(MSG_CANCEL);
        }
    }

    private void delayCancel() {
        if (mHandler != null) {
            mHandler.sendEmptyMessageDelayed(MSG_CANCEL, sMaxWaitMillis);
        }
    }

    public void resetViews() {
        ViewGroup decorView = getDecor();
        if (decorView != null) {
            TransitionManager.endTransitions(decorView);
        }
        if (mTransitioningViews != null) {
            showViews(mTransitioningViews, true);
            setTransitioningViewsVisiblity(View.VISIBLE, true);
        }
        showViews(mSharedElements, true);
        mIsHidden = true;
        if (!mIsReturning && decorView != null) {
            decorView.suppressLayout(false);
        }
        moveSharedElementsFromOverlay();
        clearState();
    }

    private void sharedElementExitBack() {
        final ViewGroup decorView = getDecor();
        if (decorView != null) {
            decorView.suppressLayout(true);
        }
        if (decorView != null && mExitSharedElementBundle != null &&
                !mExitSharedElementBundle.isEmpty() &&
                !mSharedElements.isEmpty() && getSharedElementTransition() != null) {
            startTransition(new Runnable() {
                public void run() {
                    startSharedElementExit(decorView);
                }
            });
        } else {
            sharedElementTransitionComplete();
        }
    }

    private void startSharedElementExit(final ViewGroup decorView) {
        Transition transition = getSharedElementExitTransition();
        transition.addListener(new TransitionListenerAdapter() {
            @Override
            public void onTransitionEnd(Transition transition) {
                transition.removeListener(this);
                if (isViewsTransitionComplete()) {
                    delayCancel();
                }
            }
        });
        final ArrayList<View> sharedElementSnapshots = createSnapshots(mExitSharedElementBundle,
                mSharedElementNames);
        OneShotPreDrawListener.add(decorView, () -> {
            setSharedElementState(mExitSharedElementBundle, sharedElementSnapshots);
        });
        setGhostVisibility(View.INVISIBLE);
        scheduleGhostVisibilityChange(View.INVISIBLE);
        if (mListener != null) {
            mListener.onSharedElementEnd(mSharedElementNames, mSharedElements,
                    sharedElementSnapshots);
        }
        TransitionManager.beginDelayedTransition(decorView, transition);
        scheduleGhostVisibilityChange(View.VISIBLE);
        setGhostVisibility(View.VISIBLE);
        decorView.invalidate();
    }

    private void hideSharedElements() {
        moveSharedElementsFromOverlay();
        if (mExitCallbacks != null) {
            mExitCallbacks.hideSharedElements();
        }
        if (!mIsHidden) {
            hideViews(mSharedElements);
        }
        mSharedElementsHidden = true;
        finishIfNecessary();
    }

    public void startExit() {
        if (!mIsExitStarted) {
            backgroundAnimatorComplete();
            mIsExitStarted = true;
            pauseInput();
            ViewGroup decorView = getDecor();
            if (decorView != null) {
                decorView.suppressLayout(true);
            }
            moveSharedElementsToOverlay();
            startTransition(this::beginTransitions);
        }
    }

    /**
     * Starts the exit animation and sends back the activity result
     */
    public void startExit(Activity activity) {
        int resultCode = activity.mResultCode;
        Intent data = activity.mResultData;
        if (!mIsExitStarted) {
            mIsExitStarted = true;
            pauseInput();
            ViewGroup decorView = getDecor();
            if (decorView != null) {
                decorView.suppressLayout(true);
            }
            mHandler = new Handler() {
                @Override
                public void handleMessage(Message msg) {
                    mIsCanceled = true;
                    finish();
                }
            };
            delayCancel();
            moveSharedElementsToOverlay();
            if (decorView != null && decorView.getBackground() == null) {
                getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
            }
            final boolean targetsM = decorView == null || decorView.getContext()
                    .getApplicationInfo().targetSdkVersion >= VERSION_CODES.M;
            ArrayList<String> sharedElementNames = targetsM ? mSharedElementNames :
                    mAllSharedElementNames;
            ActivityOptions options = ActivityOptions.makeSceneTransitionAnimation(activity, this,
                    sharedElementNames, resultCode, data);
            activity.convertToTranslucent(new Activity.TranslucentConversionListener() {
                @Override
                public void onTranslucentConversionComplete(boolean drawComplete) {
                    if (!mIsCanceled) {
                        fadeOutBackground();
                    }
                }
            }, options);
            startTransition(this::startExitTransition);
        }
    }

    /**
     * Called from {@link Activity#onStop()}
     */
    public void stop(Activity activity) {
        if (mIsReturning && mExitCallbacks != null) {
            // Override the previous ActivityOptions. We don't want the
            // activity to have options since we're essentially canceling the
            // transition and finishing right now.
            activity.convertToTranslucent(null, null);
            finish();
        }
    }

    private void startExitTransition() {
        Transition transition = getExitTransition();
        ViewGroup decorView = getDecor();
        if (transition != null && decorView != null && mTransitioningViews != null) {
            setTransitioningViewsVisiblity(View.VISIBLE, false);
            TransitionManager.beginDelayedTransition(decorView, transition);
            setTransitioningViewsVisiblity(View.INVISIBLE, false);
            decorView.invalidate();
        } else {
            transitionStarted();
        }
    }

    private void fadeOutBackground() {
        if (mBackgroundAnimator == null) {
            ViewGroup decor = getDecor();
            Drawable background;
            if (decor != null && (background = decor.getBackground()) != null) {
                background = background.mutate();
                getWindow().setBackgroundDrawable(background);
                mBackgroundAnimator = ObjectAnimator.ofInt(background, "alpha", 0);
                mBackgroundAnimator.addListener(new AnimatorListenerAdapter() {
                    @Override
                    public void onAnimationEnd(Animator animation) {
                        mBackgroundAnimator = null;
                        if (!mIsCanceled) {
                            mIsBackgroundReady = true;
                            notifyComplete();
                        }
                        backgroundAnimatorComplete();
                    }
                });
                mBackgroundAnimator.setDuration(getFadeDuration());
                mBackgroundAnimator.start();
            } else {
                backgroundAnimatorComplete();
                mIsBackgroundReady = true;
            }
        }
    }

    private Transition getExitTransition() {
        Transition viewsTransition = null;
        if (mTransitioningViews != null && !mTransitioningViews.isEmpty()) {
            viewsTransition = configureTransition(getViewsTransition(), true);
            removeExcludedViews(viewsTransition, mTransitioningViews);
            if (mTransitioningViews.isEmpty()) {
                viewsTransition = null;
            }
        }
        if (viewsTransition == null) {
            viewsTransitionComplete();
        } else {
            final ArrayList<View> transitioningViews = mTransitioningViews;
            viewsTransition.addListener(new ContinueTransitionListener() {
                @Override
                public void onTransitionEnd(Transition transition) {
                    viewsTransitionComplete();
                    if (mIsHidden && transitioningViews != null) {
                        showViews(transitioningViews, true);
                        setTransitioningViewsVisiblity(View.VISIBLE, true);
                    }
                    if (mSharedElementBundle != null) {
                        delayCancel();
                    }
                    super.onTransitionEnd(transition);
                }
            });
        }
        return viewsTransition;
    }

    private Transition getSharedElementExitTransition() {
        Transition sharedElementTransition = null;
        if (!mSharedElements.isEmpty()) {
            sharedElementTransition = configureTransition(getSharedElementTransition(), false);
        }
        if (sharedElementTransition == null) {
            sharedElementTransitionComplete();
        } else {
            sharedElementTransition.addListener(new ContinueTransitionListener() {
                @Override
                public void onTransitionEnd(Transition transition) {
                    sharedElementTransitionComplete();
                    if (mIsHidden) {
                        showViews(mSharedElements, true);
                    }
                    super.onTransitionEnd(transition);
                }
            });
            mSharedElements.get(0).invalidate();
        }
        return sharedElementTransition;
    }

    private void beginTransitions() {
        Transition sharedElementTransition = getSharedElementExitTransition();
        Transition viewsTransition = getExitTransition();

        Transition transition = mergeTransitions(sharedElementTransition, viewsTransition);
        ViewGroup decorView = getDecor();
        if (transition != null && decorView != null) {
            setGhostVisibility(View.INVISIBLE);
            scheduleGhostVisibilityChange(View.INVISIBLE);
            if (viewsTransition != null) {
                setTransitioningViewsVisiblity(View.VISIBLE, false);
            }
            TransitionManager.beginDelayedTransition(decorView, transition);
            scheduleGhostVisibilityChange(View.VISIBLE);
            setGhostVisibility(View.VISIBLE);
            if (viewsTransition != null) {
                setTransitioningViewsVisiblity(View.INVISIBLE, false);
            }
            decorView.invalidate();
        } else {
            transitionStarted();
        }
    }

    protected boolean isReadyToNotify() {
        return mSharedElementBundle != null && mResultReceiver != null && mIsBackgroundReady;
    }

    @Override
    protected void sharedElementTransitionComplete() {
        mSharedElementBundle = mExitSharedElementBundle == null
                ? captureSharedElementState() : captureExitSharedElementsState();
        super.sharedElementTransitionComplete();
    }

    private Bundle captureExitSharedElementsState() {
        Bundle bundle = new Bundle();
        RectF bounds = new RectF();
        Matrix matrix = new Matrix();
        for (int i = 0; i < mSharedElements.size(); i++) {
            String name = mSharedElementNames.get(i);
            Bundle sharedElementState = mExitSharedElementBundle.getBundle(name);
            if (sharedElementState != null) {
                bundle.putBundle(name, sharedElementState);
            } else {
                View view = mSharedElements.get(i);
                captureSharedElementState(view, name, bundle, matrix, bounds);
            }
        }
        return bundle;
    }

    @Override
    protected void onTransitionsComplete() {
        notifyComplete();
    }

    protected void notifyComplete() {
        if (isReadyToNotify()) {
            if (!mSharedElementNotified) {
                mSharedElementNotified = true;
                delayCancel();

                if (mExitCallbacks != null && mExitCallbacks.isReturnTransitionAllowed()) {
                    mResultReceiver.send(MSG_ALLOW_RETURN_TRANSITION, null);
                }

                if (mListener == null) {
                    mResultReceiver.send(MSG_TAKE_SHARED_ELEMENTS, mSharedElementBundle);
                    notifyExitComplete();
                } else {
                    final ResultReceiver resultReceiver = mResultReceiver;
                    final Bundle sharedElementBundle = mSharedElementBundle;
                    mListener.onSharedElementsArrived(mSharedElementNames, mSharedElements,
                            new OnSharedElementsReadyListener() {
                                @Override
                                public void onSharedElementsReady() {
                                    resultReceiver.send(MSG_TAKE_SHARED_ELEMENTS,
                                            sharedElementBundle);
                                    notifyExitComplete();
                                }
                            });
                }
            } else {
                notifyExitComplete();
            }
        }
    }

    private void notifyExitComplete() {
        if (!mExitNotified && isViewsTransitionComplete()) {
            mExitNotified = true;
            mResultReceiver.send(MSG_EXIT_TRANSITION_COMPLETE, null);
            mResultReceiver = null; // done talking
            ViewGroup decorView = getDecor();
            if (!mIsReturning && decorView != null) {
                decorView.suppressLayout(false);
            }
            finishIfNecessary();
        }
    }

    private void finishIfNecessary() {
        if (mIsReturning && mExitNotified && mExitCallbacks != null && (mSharedElements.isEmpty()
                || mSharedElementsHidden)) {
            finish();
        }
    }

    private void finish() {
        stopCancel();
        if (mExitCallbacks != null) {
            mExitCallbacks.onFinish();
            mExitCallbacks = null;
        }
        // Clear the state so that we can't hold any references accidentally and leak memory.
        clearState();
    }

    @Override
    protected void clearState() {
        mHandler = null;
        mSharedElementBundle = null;
        if (mBackgroundAnimator != null) {
            mBackgroundAnimator.cancel();
            mBackgroundAnimator = null;
        }
        mExitSharedElementBundle = null;
        super.clearState();
    }

    @Override
    protected boolean moveSharedElementWithParent() {
        return !mIsReturning;
    }

    @Override
    protected Transition getViewsTransition() {
        if (mIsReturning) {
            return getWindow().getReturnTransition();
        } else {
            return getWindow().getExitTransition();
        }
    }

    protected Transition getSharedElementTransition() {
        if (mIsReturning) {
            return getWindow().getSharedElementReturnTransition();
        } else {
            return getWindow().getSharedElementExitTransition();
        }
    }

    /**
     * @hide
     */
    public interface ExitTransitionCallbacks {

        /**
         * Returns true if reverse exit animation is supported
         */
        boolean isReturnTransitionAllowed();

        /**
         * Called then the transition finishes
         */
        void onFinish();

        /**
         * Optional callback when the transition is hiding elements in the source surface
         */
        default void hideSharedElements() { };
    }

    /**
     * @hide
     */
    public static class ActivityExitTransitionCallbacks implements ExitTransitionCallbacks {

        @NonNull
        final Activity mActivity;

        ActivityExitTransitionCallbacks(@NonNull Activity activity) {
            mActivity = activity;
        }

        @Override
        public boolean isReturnTransitionAllowed() {
            return true;
        }

        @Override
        public void onFinish() {
            mActivity.mActivityTransitionState.clear();
            mActivity.finish();
            mActivity.overridePendingTransition(0, 0);
        }
    }
}
