//------------------------------------------------------------------------------
// Copyright (c) 2005, 2006 IBM Corporation and others.
// All rights reserved. This program and the accompanying materials
// are made available under the terms of the Eclipse Public License v1.0
// which accompanies this distribution, and is available at
// http://www.eclipse.org/legal/epl-v10.html
//
// Contributors:
// IBM Corporation - initial implementation
//------------------------------------------------------------------------------
package org.eclipse.epf.authoring.ui.wizards;

import java.util.ArrayList;
import java.util.List;

import org.eclipse.core.runtime.CoreException;
import org.eclipse.epf.authoring.ui.AuthoringUIPlugin;
import org.eclipse.epf.authoring.ui.AuthoringUIResources;
import org.eclipse.epf.authoring.ui.editors.EditorChooser;
import org.eclipse.epf.authoring.ui.views.LibraryView;
import org.eclipse.epf.common.utils.StrUtil;
import org.eclipse.epf.library.ILibraryManager;
import org.eclipse.epf.library.LibraryService;
import org.eclipse.epf.library.util.ModelStorage;
import org.eclipse.epf.uma.MethodPlugin;
import org.eclipse.epf.uma.UmaFactory;
import org.eclipse.jface.viewers.IStructuredSelection;
import org.eclipse.jface.wizard.Wizard;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Display;
import org.eclipse.ui.INewWizard;
import org.eclipse.ui.IWorkbench;

/**
 * A wizard that guides the user to create a new Method Plug-in.
 * 
 * @author Shashidhar Kannoori
 * @author Kelvin Low
 * @since 1.0
 */
public class NewMethodPluginWizard extends Wizard implements INewWizard {

	/**
	 * The wizard ID.
	 */
	public static final String WIZARD_ID = NewMethodPluginWizard.class
			.getName();

	protected NewMethodPluginWizardPage mainPage;

	private MethodPlugin newPlugin;

	/**
	 * Creates a new instance.
	 */
	public NewMethodPluginWizard() {
		super();
	}

	/**
	 * @see org.eclipse.ui.IWorkbenchWizard#init(IWorkbench,
	 *      IStructuredSelection)
	 */
	public void init(IWorkbench workbench, IStructuredSelection selection) {
		setWindowTitle(AuthoringUIResources.newPluginWizard_title); //$NON-NLS-1$
	}


	/**
	 * @see org.eclipse.jface.wizard.Wizard#addPages()
	 */
	public void addPages() {
		mainPage = createMainPage();
		addPage(mainPage);
	}
	
	protected NewMethodPluginWizardPage createMainPage() {
		return new NewMethodPluginWizardPage();
	}

	/**
	 * @see org.eclipse.jface.wizard.Wizard#createPageControls(Composite)
	 */
	public void createPageControls(Composite pageContainer) {
		super.createPageControls(pageContainer);
		pageContainer.getShell().setImage(
				AuthoringUIPlugin.getDefault().getSharedImage(
						"full/obj16/MethodPlugin.gif")); //$NON-NLS-1$
	}

	/**
	 * @see org.eclipse.jface.wizard.Wizard#canFinish()
	 */
	public boolean canFinish() {
		if (LibraryService.getInstance().getCurrentMethodLibrary() == null) {
			return false;
		}
		return super.canFinish();
	}
	
	protected MethodPlugin createMethodPlugin() throws CoreException {
		String pluginName = mainPage.getPluginName();
		MethodPlugin newPlugin = UmaFactory.eINSTANCE.createMethodPlugin();
		newPlugin.setName(StrUtil.makeValidFileName(pluginName));
		newPlugin.setBriefDescription(mainPage.getBriefDescription());
		newPlugin.setAuthors(mainPage.getAuthors());
		Object[] referencedPlugins = mainPage.getReferencedPlugins();
		for (int i = 0; i < referencedPlugins.length; i++) {
			MethodPlugin plugin = (MethodPlugin) referencedPlugins[i];
			if (plugin != null) {
				newPlugin.getBases().add(plugin);
			}
		}
		ModelStorage.initialize(newPlugin);
		return newPlugin;
	}

	/**
	 * @see org.eclipse.jface.wizard.IWizard#performFinish()
	 */
	public boolean performFinish() {
		String pluginName = mainPage.getPluginName();
		if (pluginName != null && pluginName.length() > 0) {
			try {
				// Create the method plug-in and add it to the current method
				// library.
				newPlugin = createMethodPlugin();
				
				ILibraryManager manager = (ILibraryManager) LibraryService
						.getInstance().getCurrentLibraryManager();
				if (manager != null) {
					manager.addMethodPlugin(newPlugin);
				}

				Display.getCurrent().asyncExec(new Runnable() {
					public void run() {
						// Select the new Method Plug-in in the Library view.
						List selection = new ArrayList();
						selection.add(newPlugin);
						LibraryView.getView().setSelectionToViewer(selection);

						// Open the editor for newly created plug-in.
						EditorChooser.getInstance().openEditor(newPlugin);
					}
				});

				return true;
			} catch (Exception e) {
				String reason = e.getMessage() != null ? e.getMessage() : AuthoringUIResources.newPluginError_reason;
				AuthoringUIPlugin
						.getDefault()
						.getMsgDialog()
						.displayError(
						AuthoringUIResources.newPluginWizard_title, //$NON-NLS-1$
						AuthoringUIResources.newPluginError_msg, //$NON-NLS-1$
								reason,
						e);
			}
		}
		return false;
	}

}