/*
 * Copyright 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 com.android.ex.camera2.blocking;

import android.hardware.camera2.CameraCaptureSession;
import android.os.ConditionVariable;
import android.os.SystemClock;
import android.util.Log;
import android.view.Surface;

import com.android.ex.camera2.exceptions.TimeoutRuntimeException;
import com.android.ex.camera2.utils.StateChangeListener;
import com.android.ex.camera2.utils.StateWaiter;

import java.util.List;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.concurrent.Future;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException;


/**
 * A camera session listener that implements blocking operations on session state changes.
 *
 * <p>Provides a waiter that can be used to block until the next unobserved state of the
 * requested type arrives.</p>
 *
 * <p>Pass-through all StateCallback changes to the proxy.</p>
 *
 * @see #getStateWaiter
 */
public class BlockingSessionCallback extends CameraCaptureSession.StateCallback {
    /**
     * Session is configured, ready for captures
     */
    public static final int SESSION_CONFIGURED = 0;

    /**
     * Session has failed to configure, can't do any captures
     */
    public static final int SESSION_CONFIGURE_FAILED = 1;

    /**
     * Session is ready
     */
    public static final int SESSION_READY = 2;

    /**
     * Session is active (transitory)
     */
    public static final int SESSION_ACTIVE = 3;

    /**
     * Session is closed
     */
    public static final int SESSION_CLOSED = 4;

    private static final int NUM_STATES = 5;

    /*
     * Private fields
     */
    private static final String TAG = "BlockingSessionCallback";
    private static final boolean VERBOSE = Log.isLoggable(TAG, Log.VERBOSE);

    private final CameraCaptureSession.StateCallback mProxy;
    private final SessionFuture mSessionFuture = new SessionFuture();

    private final StateWaiter mStateWaiter = new StateWaiter(sStateNames);
    private final StateChangeListener mStateChangeListener = mStateWaiter.getListener();
    private final HashMap<CameraCaptureSession, List<Surface> > mPreparedSurfaces = new HashMap<>();

    private static final String[] sStateNames = {
        "SESSION_CONFIGURED",
        "SESSION_CONFIGURE_FAILED",
        "SESSION_READY",
        "SESSION_ACTIVE",
        "SESSION_CLOSED"
    };

    /**
     * Create a blocking session listener without forwarding the session listener invocations
     * to another session listener.
     */
    public BlockingSessionCallback() {
        mProxy = null;
    }

    /**
     * Create a blocking session listener; forward original listener invocations
     * into {@code listener}.
     *
     * @param listener a non-{@code null} listener to forward invocations into
     *
     * @throws NullPointerException if {@code listener} was {@code null}
     */
    public BlockingSessionCallback(CameraCaptureSession.StateCallback listener) {
        if (listener == null) {
            throw new NullPointerException("listener must not be null");
        }
        mProxy = listener;
    }

    /**
     * Acquire the state waiter; can be used to block until a set of state transitions have
     * been reached.
     *
     * <p>Only one thread should wait at a time.</p>
     */
    public StateWaiter getStateWaiter() {
        return mStateWaiter;
    }

    /**
     * Return session if already have it; otherwise wait until any of the session listener
     * invocations fire and the session is available.
     *
     * <p>Does not consume any of the states from the state waiter.</p>
     *
     * @param timeoutMs how many milliseconds to wait for
     * @return a non-{@code null} {@link CameraCaptureSession} instance
     *
     * @throws TimeoutRuntimeException if waiting for more than {@long timeoutMs}
     */
    public CameraCaptureSession waitAndGetSession(long timeoutMs) {
        try {
            return mSessionFuture.get(timeoutMs, TimeUnit.MILLISECONDS);
        } catch (TimeoutException e) {
            throw new TimeoutRuntimeException(
                    String.format("Failed to get session after %s milliseconds", timeoutMs), e);
        }
    }

    /*
     * CameraCaptureSession.StateCallback implementation
     */

    @Override
    public void onActive(CameraCaptureSession session) {
        mSessionFuture.setSession(session);
        if (mProxy != null) mProxy.onActive(session);
        mStateChangeListener.onStateChanged(SESSION_ACTIVE);
    }

    @Override
    public void onClosed(CameraCaptureSession session) {
        mSessionFuture.setSession(session);
        if (mProxy != null) mProxy.onClosed(session);
        mStateChangeListener.onStateChanged(SESSION_CLOSED);
        synchronized (mPreparedSurfaces) {
            mPreparedSurfaces.remove(session);
        }
    }

    @Override
    public void onConfigured(CameraCaptureSession session) {
        mSessionFuture.setSession(session);
        if (mProxy != null) {
            mProxy.onConfigured(session);
        }
        mStateChangeListener.onStateChanged(SESSION_CONFIGURED);
    }

    @Override
    public void onConfigureFailed(CameraCaptureSession session) {
        mSessionFuture.setSession(session);
        if (mProxy != null) {
            mProxy.onConfigureFailed(session);
        }
        mStateChangeListener.onStateChanged(SESSION_CONFIGURE_FAILED);
    }

    @Override
    public void onReady(CameraCaptureSession session) {
        mSessionFuture.setSession(session);
        if (mProxy != null) {
            mProxy.onReady(session);
        }
        mStateChangeListener.onStateChanged(SESSION_READY);
    }

    @Override
    public void onSurfacePrepared(CameraCaptureSession session, Surface surface) {
        mSessionFuture.setSession(session);
        if (mProxy != null) {
            mProxy.onSurfacePrepared(session, surface);
        }
        // Surface prepared doesn't cause a session state change, so don't trigger the
        // state change listener
        synchronized (mPreparedSurfaces) {
            List<Surface> preparedSurfaces = mPreparedSurfaces.get(session);
            if (preparedSurfaces == null) {
                preparedSurfaces = new ArrayList<Surface>();
            }
            preparedSurfaces.add(surface);
            mPreparedSurfaces.put(session, preparedSurfaces);
            mPreparedSurfaces.notifyAll();
        }
    }

    /**
     * Wait until the designated surface is prepared by the camera capture session.
     *
     * @param session the input {@link CameraCaptureSession} to wait for
     * @param surface the input {@link Surface} to wait for
     * @param timeoutMs how many milliseconds to wait for
     *
     * @throws TimeoutRuntimeException if waiting for more than {@long timeoutMs}
     */
    public void waitForSurfacePrepared(
            CameraCaptureSession session, Surface surface, long timeoutMs) {
        synchronized (mPreparedSurfaces) {
            List<Surface> preparedSurfaces = mPreparedSurfaces.get(session);
            if (preparedSurfaces != null && preparedSurfaces.contains(surface)) {
                return;
            }
            try {
                long waitTimeRemaining = timeoutMs;
                while (waitTimeRemaining > 0) {
                    long waitStartTime = SystemClock.elapsedRealtime();
                    mPreparedSurfaces.wait(timeoutMs);
                    long waitTime = SystemClock.elapsedRealtime() - waitStartTime;
                    waitTimeRemaining -= waitTime;
                    preparedSurfaces = mPreparedSurfaces.get(session);
                    if (waitTimeRemaining >= 0 && preparedSurfaces != null &&
                            preparedSurfaces.contains(surface)) {
                        return;
                    }
                }
                throw new TimeoutRuntimeException(
                        "Unable to get Surface prepared in " + timeoutMs + "ms");
            } catch (InterruptedException ie) {
                throw new AssertionError();
            }
        }
    }

    private static class SessionFuture implements Future<CameraCaptureSession> {
        private volatile CameraCaptureSession mSession;
        ConditionVariable mCondVar = new ConditionVariable(/*opened*/false);

        public void setSession(CameraCaptureSession session) {
            mSession = session;
            mCondVar.open();
        }

        @Override
        public boolean cancel(boolean mayInterruptIfRunning) {
            return false; // don't allow canceling this task
        }

        @Override
        public boolean isCancelled() {
            return false; // can never cancel this task
        }

        @Override
        public boolean isDone() {
            return mSession != null;
        }

        @Override
        public CameraCaptureSession get() {
            mCondVar.block();
            return mSession;
        }

        @Override
        public CameraCaptureSession get(long timeout, TimeUnit unit) throws TimeoutException {
            long timeoutMs = unit.convert(timeout, TimeUnit.MILLISECONDS);
            if (!mCondVar.block(timeoutMs)) {
                throw new TimeoutException(
                        "Failed to receive session after " + timeout + " " + unit);
            }

            if (mSession == null) {
                throw new AssertionError();
            }
            return mSession;
        }

    }
}
