/*
 * Copyright (C) 2011 The Android Open Source Project
 *
 * Licensed under the Eclipse Public License, Version 1.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.eclipse.org/org/documents/epl-v10.php
 *
 * 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.ide.eclipse.adt.internal.wizards.newproject;

import com.android.SdkConstants;
import com.android.ide.eclipse.adt.AdtPlugin;
import com.android.ide.eclipse.adt.internal.wizards.newproject.NewProjectWizardState.Mode;
import com.android.sdklib.IAndroidTarget;
import com.android.utils.Pair;

import org.eclipse.core.runtime.IStatus;
import org.eclipse.core.runtime.Path;
import org.eclipse.core.runtime.Platform;
import org.eclipse.core.runtime.Status;
import org.eclipse.jface.dialogs.IMessageProvider;
import org.eclipse.jface.viewers.ArrayContentProvider;
import org.eclipse.jface.viewers.ColumnLabelProvider;
import org.eclipse.jface.viewers.IBaseLabelProvider;
import org.eclipse.jface.viewers.TableViewer;
import org.eclipse.jface.wizard.WizardPage;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.ModifyEvent;
import org.eclipse.swt.events.ModifyListener;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.events.SelectionListener;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Label;
import org.eclipse.swt.widgets.Table;
import org.eclipse.swt.widgets.Text;

import java.io.File;

/** Page where the user can select a sample to "instantiate" */
class SampleSelectionPage extends WizardPage implements SelectionListener, ModifyListener {
    private final NewProjectWizardState mValues;
    private boolean mIgnore;

    private Table mTable;
    private TableViewer mTableViewer;
    private IAndroidTarget mCurrentSamplesTarget;
    private Text mSampleProjectName;

    /**
     * Create the wizard.
     */
    SampleSelectionPage(NewProjectWizardState values) {
        super("samplePage"); //$NON-NLS-1$
        setTitle("Select Sample");
        setDescription("Select which sample to create");
        mValues = values;
    }

    /**
     * Create contents of the wizard.
     */
    @Override
    public void createControl(Composite parent) {
        Composite container = new Composite(parent, SWT.NULL);
        container.setLayout(new GridLayout(2, false));

        mTableViewer = new TableViewer(container, SWT.BORDER | SWT.FULL_SELECTION);
        mTable = mTableViewer.getTable();
        GridData gridData = new GridData(SWT.FILL, SWT.FILL, true, true, 2, 1);
        gridData.heightHint = 300;
        mTable.setLayoutData(gridData);
        mTable.addSelectionListener(this);

        setControl(container);

        Label projectLabel = new Label(container, SWT.NONE);
        projectLabel.setLayoutData(new GridData(SWT.RIGHT, SWT.CENTER, false, false, 1, 1));
        projectLabel.setText("Project Name:");

        mSampleProjectName = new Text(container, SWT.BORDER);
        mSampleProjectName.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false, 1, 1));
        mSampleProjectName.addModifyListener(this);
    }

    @Override
    public void setVisible(boolean visible) {
        super.setVisible(visible);

        if (visible) {
            if (mValues.projectName != null) {
                try {
                    mIgnore = true;
                    mSampleProjectName.setText(mValues.projectName);
                } finally {
                    mIgnore = false;
                }
            }

            // Update samples list if the SDK target has changed (or if it hasn't yet
            // been populated)
            if (mCurrentSamplesTarget != mValues.target) {
                mCurrentSamplesTarget = mValues.target;
                updateSamples();
            }

            validatePage();
        }
    }

    private void updateSamples() {
        IBaseLabelProvider labelProvider = new ColumnLabelProvider() {
            @Override
            public Image getImage(Object element) {
                return AdtPlugin.getAndroidLogo();
            }

            @Override
            public String getText(Object element) {
                if (element instanceof Pair<?, ?>) {
                    Object name = ((Pair<?, ?>) element).getFirst();
                    return name.toString();
                }
                return element.toString(); // Fallback. Should not happen.
            }
        };

        mTableViewer.setContentProvider(new ArrayContentProvider());
        mTableViewer.setLabelProvider(labelProvider);

        if (mValues.samples != null && mValues.samples.size() > 0) {
            Object[] samples = mValues.samples.toArray();
            mTableViewer.setInput(samples);

            mTable.select(0);
            selectSample(mValues.samples.get(0).getSecond());
            extractNamesFromAndroidManifest();
        }
    }

    private void selectSample(File sample) {
        mValues.chosenSample = sample;
        if (sample != null && !mValues.projectNameModifiedByUser) {
            mValues.projectName = sample.getName();
            if (SdkConstants.FD_SAMPLE.equals(mValues.projectName) &&
                    sample.getParentFile() != null) {
                mValues.projectName = sample.getParentFile().getName() + '_' + mValues.projectName;
            }
            try {
                mIgnore = true;
                mSampleProjectName.setText(mValues.projectName);
            } finally {
                mIgnore = false;
            }
            updatedProjectName();
        }
    }

    @SuppressWarnings("unchecked")
    @Override
    public void widgetSelected(SelectionEvent e) {
        if (mIgnore) {
            return;
        }

        if (e.getSource() == mTable) {
            extractNamesFromAndroidManifest();
            int index = mTable.getSelectionIndex();
            if (index >= 0) {
                Object[] roots = (Object[]) mTableViewer.getInput();
                selectSample(((Pair<String, File>) roots[index]).getSecond());
            } else {
                selectSample(null);
            }
        } else {
            assert false : e.getSource();
        }

        validatePage();
    }

    @Override
    public void widgetDefaultSelected(SelectionEvent e) {
    }

    @Override
    public void modifyText(ModifyEvent e) {
        if (mIgnore) {
            return;
        }

        if (e.getSource() == mSampleProjectName) {
            mValues.projectName = mSampleProjectName.getText().trim();
            mValues.projectNameModifiedByUser = true;
            updatedProjectName();
        }

        validatePage();
    }

    private void updatedProjectName() {
        if (mValues.useDefaultLocation) {
            mValues.projectLocation = Platform.getLocation().toFile();
        }
    }

    /**
     * A sample was selected. Update the location field, manifest and validate.
     * Extract names from an android manifest.
     * This is done only if the user selected the "use existing source" and a manifest xml file
     * can actually be found in the custom user directory.
     */
    private void extractNamesFromAndroidManifest() {
        if (mValues.chosenSample == null || !mValues.chosenSample.isDirectory()) {
            return;
        }

        Path path = new Path(mValues.chosenSample.getPath());
        mValues.extractFromAndroidManifest(path);
    }

    @Override
    public boolean isPageComplete() {
        if (mValues.mode != Mode.SAMPLE) {
            return true;
        }

        // Ensure that when creating samples, the Finish button isn't enabled until
        // the user has reached and completed this page
        if (mValues.chosenSample == null) {
            return false;
        }

        return super.isPageComplete();
    }

    private void validatePage() {
        IStatus status = null;
        if (mValues.samples == null || mValues.samples.size() == 0) {
            status = new Status(IStatus.ERROR, AdtPlugin.PLUGIN_ID,
                    "The chosen SDK does not contain any samples");
        } else if (mValues.chosenSample == null) {
            status = new Status(IStatus.ERROR, AdtPlugin.PLUGIN_ID, "Choose a sample");
        } else if (!mValues.chosenSample.exists()) {
            status = new Status(IStatus.ERROR, AdtPlugin.PLUGIN_ID,
                    String.format("Sample does not exist: %1$s", mValues.chosenSample.getPath()));
        } else {
            status = ProjectNamePage.validateProjectName(mValues.projectName);
        }

        // -- update UI & enable finish if there's no error
        setPageComplete(status == null || status.getSeverity() != IStatus.ERROR);
        if (status != null) {
            setMessage(status.getMessage(),
                    status.getSeverity() == IStatus.ERROR
                        ? IMessageProvider.ERROR : IMessageProvider.WARNING);
        } else {
            setErrorMessage(null);
            setMessage(null);
        }
    }
}
