/*
 * Copyright (C) 2011 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.camera;

import com.android.camera.ui.PopupManager;
import com.android.camera.ui.Rotatable;
import com.android.camera.ui.RotateImageView;

import android.content.Context;
import android.graphics.PorterDuff;
import android.graphics.drawable.Drawable;
import android.util.AttributeSet;
import android.util.Log;
import android.view.View;
import android.view.animation.Animation;
import android.view.animation.Animation.AnimationListener;
import android.view.animation.AnimationUtils;
import android.widget.ImageView;
import android.widget.RelativeLayout;

/**
 * A widget that includes three mode selections {@code RotateImageView}'s and
 * a current mode indicator.
 */
public class ModePicker extends RelativeLayout implements View.OnClickListener,
    PopupManager.OnOtherPopupShowedListener, Rotatable {
    public static final int MODE_CAMERA = 0;
    public static final int MODE_VIDEO = 1;
    public static final int MODE_PANORAMA = 2;

    private static final String TAG = "ModePicker";
    // Total mode number
    private static final int MODE_NUM = 3;

    /** A callback to be called when the user wants to switch activity. */
    public interface OnModeChangeListener {
        // Returns true if the listener agrees that the mode can be changed.
        public boolean onModeChanged(int newMode);
    }

    private final int DISABLED_COLOR;
    private final int CURRENT_MODE_BACKGROUND;

    private OnModeChangeListener mListener;
    private View mModeSelectionFrame;
    private RotateImageView mModeSelectionIcon[];
    private View mCurrentModeFrame;
    private RotateImageView mCurrentModeIcon[];
    private View mCurrentModeBar;
    private boolean mSelectionEnabled;


    private int mCurrentMode = 0;
    private Animation mFadeIn, mFadeOut;

    public ModePicker(Context context, AttributeSet attrs) {
        super(context, attrs);
        DISABLED_COLOR = context.getResources().getColor(R.color.icon_disabled_color);
        CURRENT_MODE_BACKGROUND = R.drawable.btn_mode_background;
        mFadeIn = AnimationUtils.loadAnimation(
                context, R.anim.mode_selection_fade_in);
        mFadeOut = AnimationUtils.loadAnimation(
                context, R.anim.mode_selection_fade_out);
        mFadeOut.setAnimationListener(mAnimationListener);
        PopupManager.getInstance(context).setOnOtherPopupShowedListener(this);
    }

    protected void onFinishInflate() {
        super.onFinishInflate();

        mModeSelectionFrame = findViewById(R.id.mode_selection);
        mModeSelectionIcon = new RotateImageView[MODE_NUM];
        mModeSelectionIcon[MODE_PANORAMA] =
                (RotateImageView) findViewById(R.id.mode_panorama);
        mModeSelectionIcon[MODE_VIDEO] =
                (RotateImageView) findViewById(R.id.mode_video);
        mModeSelectionIcon[MODE_CAMERA] =
                (RotateImageView) findViewById(R.id.mode_camera);

        // The current mode frame is for Phone UI only.
        mCurrentModeFrame = findViewById(R.id.current_mode);
        if (mCurrentModeFrame != null) {
            mCurrentModeIcon = new RotateImageView[MODE_NUM];
            mCurrentModeIcon[0] = (RotateImageView) findViewById(R.id.mode_0);
            mCurrentModeIcon[1] = (RotateImageView) findViewById(R.id.mode_1);
            mCurrentModeIcon[2] = (RotateImageView) findViewById(R.id.mode_2);
        } else {
            // current_mode_bar is only for tablet.
            mCurrentModeBar = findViewById(R.id.current_mode_bar);
            enableModeSelection(true);
        }
        registerOnClickListener();
    }

    private void registerOnClickListener() {
        if (mCurrentModeFrame != null) {
            mCurrentModeFrame.setOnClickListener(this);
        }
        for (int i = 0; i < MODE_NUM; ++i) {
            mModeSelectionIcon[i].setOnClickListener(this);
        }
    }

    @Override
    public void onOtherPopupShowed() {
        if (mSelectionEnabled) enableModeSelection(false);
    }

    private AnimationListener mAnimationListener = new AnimationListener() {
        public void onAnimationEnd(Animation animation) {
            changeToSelectedMode();
            mCurrentModeFrame.setVisibility(View.VISIBLE);
            mModeSelectionFrame.setVisibility(View.GONE);
        }

        public void onAnimationRepeat(Animation animation) {
        }

        public void onAnimationStart(Animation animation) {
        }
    };

    private void enableModeSelection(boolean enabled) {
        if (mCurrentModeFrame != null) {
            mSelectionEnabled = enabled;
            // Animation Effect is applied on Phone UI only.
            mModeSelectionFrame.startAnimation(enabled ? mFadeIn : mFadeOut);
            if (enabled) {
                mModeSelectionFrame.setVisibility(View.VISIBLE);
                mCurrentModeFrame.setVisibility(View.GONE);
            }
        }
        updateModeState();
    }

    private void changeToSelectedMode() {
        if (mListener != null) {
            if (mListener.onModeChanged(mCurrentMode)) {
                Log.e(TAG, "failed:onModeChanged:" + mCurrentMode);
            }
        }
    }

    public void onClick(View view) {
        if (view == mCurrentModeFrame) {
            PopupManager.getInstance(getContext()).notifyShowPopup(this);
            enableModeSelection(true);
        } else {
            // Set the selected mode as the current one and switch to it.
            for (int i = 0; i < MODE_NUM; ++i) {
                if (view == mModeSelectionIcon[i] && (mCurrentMode != i)) {
                    setCurrentMode(i);
                    break;
                }
            }
            if (mCurrentModeBar == null) {
                enableModeSelection(false);
            } else {
                changeToSelectedMode();
            }
        }
    }

    public void setOnModeChangeListener(OnModeChangeListener listener) {
        mListener = listener;
    }

    public void setCurrentMode(int mode) {
        mCurrentMode = mode;
        updateModeState();
    }

    public boolean onModeChanged(int mode) {
        setCurrentMode(mode);
        return true;
    }

    public void setOrientation(int orientation) {
        for (int i = 0; i < MODE_NUM; ++i) {
            mModeSelectionIcon[i].setOrientation(orientation);
            if (mCurrentModeFrame != null) {
                mCurrentModeIcon[i].setOrientation(orientation);
            }
        }
    }

    @Override
    public void setEnabled(boolean enabled) {
        super.setEnabled(enabled);

        // Enable or disable the frames.
        if (mCurrentModeFrame != null) mCurrentModeFrame.setEnabled(enabled);
        mModeSelectionFrame.setEnabled(enabled);

        // Enable or disable the icons.
        for (int i = 0; i < MODE_NUM; ++i) {
            mModeSelectionIcon[i].setEnabled(enabled);
            if (mCurrentModeFrame != null) mCurrentModeIcon[i].setEnabled(enabled);
        }
        if (enabled) updateModeState();
    }

    private void highlightView(ImageView view, boolean enabled) {
        if (enabled) {
            view.clearColorFilter();
        } else {
            view.setColorFilter(DISABLED_COLOR, PorterDuff.Mode.SRC_ATOP);
        }
    }

    private void updateModeState() {
        // Grey-out the unselected icons for Phone UI.
        if (mCurrentModeFrame != null) {
            for (int i = 0; i < MODE_NUM; ++i) {
                highlightView(mModeSelectionIcon[i], (i == mCurrentMode));
            }
        }

        // Update the current mode icons on the Phone UI. The selected mode
        // should be in the center of the current mode icon bar.
        if (mCurrentModeFrame != null) {
            for (int i = 0, j = 0; i < MODE_NUM; ++i) {
                int target;
                if (i == 1) {
                    // The second icon is always the selected mode.
                    target = mCurrentMode;
                } else {
                    // Set the icons in order of camera, video and panorama.
                    if (j == mCurrentMode) j++;
                    target = j++;
                }
                mCurrentModeIcon[i].setImageDrawable(
                        mModeSelectionIcon[target].getDrawable());
            }
        }
    }

    @Override
    protected void onLayout(
            boolean changed, int left, int top, int right, int bottom) {
        super.onLayout(changed, left, top, right, bottom);
        // Layout the current mode indicator bar.
        if (mCurrentModeBar != null) {
            int viewWidth = mModeSelectionIcon[MODE_CAMERA].getWidth();
            int iconWidth = ((ImageView) mModeSelectionIcon[MODE_CAMERA])
                    .getDrawable().getIntrinsicWidth();
            int padding = (viewWidth - iconWidth) / 2;
            int l = mModeSelectionFrame.getLeft() + mCurrentMode * viewWidth;
            mCurrentModeBar.layout((l + padding),
                    (bottom - top - mCurrentModeBar.getHeight()),
                    (l + padding + iconWidth),
                    (bottom - top));
        }
    }
}
