/*******************************************************************************
 * Copyright (c) 2003, 2004 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 API and implementation
 *******************************************************************************/
/*
 * Created on Dec 8, 2003
 * 
 * To change the template for this generated file go to Window>Preferences>Java>Code Generation>Code and Comments
 */
package org.eclipse.jst.j2ee.internal.wizard;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
import java.util.List;

import org.eclipse.jface.viewers.CellEditor;
import org.eclipse.jface.viewers.CheckStateChangedEvent;
import org.eclipse.jface.viewers.CheckboxTableViewer;
import org.eclipse.jface.viewers.ColumnWeightData;
import org.eclipse.jface.viewers.ICellModifier;
import org.eclipse.jface.viewers.ICheckStateListener;
import org.eclipse.jface.viewers.TableLayout;
import org.eclipse.jface.viewers.TextCellEditor;
import org.eclipse.jst.j2ee.application.operations.EARImportDataModel;
import org.eclipse.jst.j2ee.application.operations.J2EEImportDataModel;
import org.eclipse.jst.j2ee.internal.actions.IJ2EEUIContextIds;
import org.eclipse.jst.j2ee.internal.plugin.J2EEUIMessages;
import org.eclipse.jst.j2ee.internal.plugin.J2EEUIPlugin;
import org.eclipse.jst.j2ee.internal.plugin.J2EEUIPluginIcons;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.layout.GridData;
import org.eclipse.swt.layout.GridLayout;
import org.eclipse.swt.widgets.Button;
import org.eclipse.swt.widgets.Composite;
import org.eclipse.swt.widgets.Table;
import org.eclipse.swt.widgets.TableColumn;
import org.eclipse.swt.widgets.TableItem;
import org.eclipse.wst.common.frameworks.internal.operations.WTPOperationDataModelEvent;

import com.ibm.wtp.emf.workbench.ProjectUtilities;

/**
 * @author cbridgha
 * 
 * To change the template for this generated type comment go to Window>Preferences>Java>Code
 * Generation>Code and Comments
 */
public class EARImportProjectsPage extends J2EEImportPage implements ICellModifier {

	private CheckboxTableViewer earFileListViewer;

	public static final String INCLUDE_COLUMN = J2EEUIMessages.getResourceString("EARImportProjectsPage_UI_0"); //$NON-NLS-1$
	public static final String FILE_COLUMN = J2EEUIMessages.getResourceString("EARImportProjectsPage_UI_1"); //$NON-NLS-1$
	public static final String PROJECT_COLUMN = J2EEUIMessages.getResourceString("EARImportProjectsPage_UI_2"); //$NON-NLS-1$

	/**
	 * @param model
	 * @param pageName
	 */
	public EARImportProjectsPage(J2EEImportDataModel model, String pageName) {
		super(model, pageName);
		setTitle(J2EEUIMessages.getResourceString(J2EEUIMessages.EAR_IMPORT_PROJECT_PG_TITLE));
		setDescription(J2EEUIMessages.getResourceString(J2EEUIMessages.EAR_IMPORT_PROJECT_PG_DESC));
		setImageDescriptor(J2EEUIPlugin.getDefault().getImageDescriptor(J2EEUIPluginIcons.EAR_IMPORT_WIZARD_BANNER));
	}

	protected Composite createTopLevelComposite(Composite parent) {
		Composite composite = new Composite(parent, SWT.NONE);
		setInfopopID(IJ2EEUIContextIds.IMPORT_EAR_WIZARD_P3);
		GridLayout layout = new GridLayout();
		composite.setLayout(layout);
		composite.setLayoutData(new GridData(GridData.FILL_HORIZONTAL));
		EARImportOptionsPage.createNestedProjectOverwriteCheckbox(synchHelper, composite);
		createListGroup(composite);
		createButtonsGroup(composite);

		return composite;
	}

	protected void setColumnEditors() {
		Table t = earFileListViewer.getTable();
		CellEditor[] columnEditors = new CellEditor[t.getColumnCount()];
		columnEditors[1] = new TextCellEditor(t);

		earFileListViewer.setCellEditors(columnEditors);
	}

	protected void createButtonsGroup(Composite parent) {
		Composite buttonGroup = new Composite(parent, SWT.NONE);
		GridLayout layout = new GridLayout();
		layout.numColumns = 4;
		buttonGroup.setLayout(layout);
		buttonGroup.setLayoutData(new GridData(GridData.FILL_BOTH));

		Button selectNotInWorkspace = new Button(buttonGroup, SWT.PUSH);
		selectNotInWorkspace.setText(J2EEUIMessages.getResourceString("EARImportProjectsPage_UI_3")); //$NON-NLS-1$
		GridData gd = new GridData(GridData.HORIZONTAL_ALIGN_FILL);
		gd.horizontalSpan = 1;
		gd.heightHint = 22;
		gd.widthHint = 120;
		selectNotInWorkspace.setLayoutData(gd);
		selectNotInWorkspace.addSelectionListener(new SelectionAdapter() {
			public void widgetSelected(SelectionEvent e) {
				List list = getEARImportDataModel().getProjectModels();
				List selectedList = getEARImportDataModel().getSelectedModels();
				List newList = new ArrayList();
				newList.addAll(selectedList);
				J2EEImportDataModel importDM = null;
				for (int i = 0; i < list.size(); i++) {
					importDM = (J2EEImportDataModel) list.get(i);
					if (!newList.contains(importDM) && !importDM.getProject().exists()) {
						newList.add(importDM);
					}
				}
				getEARImportDataModel().setProperty(EARImportDataModel.SELECTED_MODELS_LIST, newList);
			}
		});

		Button selectBinary = new Button(buttonGroup, SWT.PUSH);
		selectBinary.setText(J2EEUIMessages.getResourceString("EARImportProjectsPage_UI_4")); //$NON-NLS-1$
		gd = new GridData(GridData.HORIZONTAL_ALIGN_FILL);
		gd.horizontalSpan = 1;
		gd.heightHint = 22;
		gd.widthHint = 120;
		selectBinary.setLayoutData(gd);
		selectBinary.addSelectionListener(new SelectionAdapter() {
			public void widgetSelected(SelectionEvent e) {
				List list = getEARImportDataModel().getProjectModels();
				List selectedList = getEARImportDataModel().getSelectedModels();
				List newList = new ArrayList();
				newList.addAll(selectedList);
				J2EEImportDataModel importDM = null;
				for (int i = 0; i < list.size(); i++) {
					importDM = (J2EEImportDataModel) list.get(i);
					if (!newList.contains(importDM) && ProjectUtilities.isBinaryProject(importDM.getProject())) {
						newList.add(importDM);
					}
				}
				getEARImportDataModel().setProperty(EARImportDataModel.SELECTED_MODELS_LIST, newList);
			}
		});

		Button selectAllButton = new Button(buttonGroup, SWT.PUSH);
		selectAllButton.setText(J2EEUIMessages.getResourceString(J2EEUIMessages.EAR_IMPORT_SELECT_ALL_UTIL_BUTTON));
		gd = new GridData(GridData.HORIZONTAL_ALIGN_FILL);
		gd.horizontalSpan = 1;
		gd.heightHint = 22;
		gd.widthHint = 120;
		selectAllButton.setLayoutData(gd);
		selectAllButton.addSelectionListener(new SelectionAdapter() {
			public void widgetSelected(SelectionEvent e) {
				List list = getEARImportDataModel().getProjectModels();
				List newList = new ArrayList();
				newList.addAll(list);
				getEARImportDataModel().setProperty(EARImportDataModel.SELECTED_MODELS_LIST, newList);
			}
		});

		Button deselectAllButton = new Button(buttonGroup, SWT.PUSH);
		deselectAllButton.setText(J2EEUIMessages.getResourceString(J2EEUIMessages.EAR_IMPORT_DESELECT_ALL_UTIL_BUTTON));
		gd = new GridData(GridData.HORIZONTAL_ALIGN_FILL);
		gd.horizontalSpan = 1;
		gd.heightHint = 22;
		gd.widthHint = 120;
		deselectAllButton.setLayoutData(gd);
		deselectAllButton.addSelectionListener(new SelectionAdapter() {
			public void widgetSelected(SelectionEvent e) {
				List newList = new ArrayList();
				getEARImportDataModel().setProperty(EARImportDataModel.SELECTED_MODELS_LIST, newList);
			}
		});
	}

	public void propertyChanged(WTPOperationDataModelEvent event) {
		if (event.getPropertyName().equals(EARImportDataModel.SELECTED_MODELS_LIST)) {
			updateGUICheckSelection();
		}
		super.propertyChanged(event);
	}

	public void setFileListViewerInput() {
		TableObjects files = new TableObjects();
		Iterator iterator = getEARImportDataModel().getProjectModels().iterator();
		while (iterator.hasNext()) {
			files.tableObjectsList.add(iterator.next());
		}
		earFileListViewer.setInput(files);
		updateGUICheckSelection();
	}

	private void updateGUICheckSelection() {
		List selectedList = getEARImportDataModel().getSelectedModels();
		List projectList = getEARImportDataModel().getProjectModels();
		Object currentElement = null;
		for (int i = 0; i < projectList.size(); i++) {
			currentElement = projectList.get(i);
			earFileListViewer.setChecked(currentElement, selectedList.contains(currentElement));
		}
	}

	/**
	 * @see org.eclipse.jst.j2ee.internal.internal.internal.wizard.J2EEWizardPage#enter()
	 */
	protected void enter() {
		super.enter();
		setFileListViewerInput();
		validatePage();
	}

	/**
	 * Creates the import source specification widgets. <b>Subclasses </b> must override this hook
	 * method.
	 * 
	 * @param parent
	 *            a <code>Composite</code> that is to be used as the parent of this group's
	 *            collection of visual components
	 * @see org.eclipse.swt.widgets.Composite
	 */
	protected void createListGroup(org.eclipse.swt.widgets.Composite parent) {
		Composite listGroup = new Composite(parent, SWT.NONE);
		GridLayout layout = new GridLayout();
		layout.numColumns = 1;
		listGroup.setLayout(layout);
		GridData gd = new GridData(GridData.FILL_BOTH | GridData.GRAB_HORIZONTAL);
		listGroup.setLayoutData(gd);

		earFileListViewer = CheckboxTableViewer.newCheckList(listGroup, SWT.BORDER | SWT.H_SCROLL | SWT.V_SCROLL | SWT.FULL_SELECTION);
		EARImportListContentProvider provider = new EARImportListContentProvider();
		earFileListViewer.setContentProvider(provider);
		earFileListViewer.setLabelProvider(provider);
		earFileListViewer.addCheckStateListener(new ICheckStateListener() {
			public void checkStateChanged(CheckStateChangedEvent event) {
				J2EEImportDataModel aModel = (J2EEImportDataModel) event.getElement();
				J2EEImportDataModel matchingModel = getEARImportDataModel().getMatchingEJBJarOrClient(aModel);
				if (null != matchingModel) {
					earFileListViewer.setChecked(matchingModel, event.getChecked());
				}
				List result = new ArrayList();
				result.addAll(Arrays.asList(earFileListViewer.getCheckedElements()));
				getEARImportDataModel().setProperty(EARImportDataModel.SELECTED_MODELS_LIST, result);

			}
		});

		Table earFileListTable = (Table) earFileListViewer.getControl();
		earFileListTable.setHeaderVisible(true);
		earFileListTable.setLinesVisible(true);
		// set up table layout
		TableLayout tableLayout = new org.eclipse.jface.viewers.TableLayout();
		tableLayout.addColumnData(new ColumnWeightData(100, true));
		tableLayout.addColumnData(new ColumnWeightData(200, true));
		earFileListTable.setLayout(tableLayout);

		gd = new GridData(GridData.FILL_BOTH | GridData.GRAB_HORIZONTAL | GridData.GRAB_VERTICAL);
		gd.widthHint = 400;
		earFileListTable.setLayoutData(gd);


		TableColumn fileNameColumns = new TableColumn(earFileListTable, SWT.NONE);
		fileNameColumns.setText(J2EEUIMessages.getResourceString(J2EEUIMessages.EAR_IMPORT_Modules_in_EAR)); //$NON-NLS-1$ = "Modules in EAR"
		fileNameColumns.setResizable(true);

		TableColumn importNameColumn = new TableColumn(earFileListTable, SWT.NONE);
		importNameColumn.setText(J2EEUIMessages.getResourceString(J2EEUIMessages.EAR_IMPORT_New_Project_Name)); //$NON-NLS-1$ = "New Project Name"
		importNameColumn.setResizable(true);

		String[] columnProperties = new String[2];
		columnProperties[0] = FILE_COLUMN;
		columnProperties[1] = PROJECT_COLUMN;
		earFileListViewer.setColumnProperties(columnProperties);

		setColumnEditors();
		earFileListViewer.setCellModifier(this);
	}

	private EARImportDataModel getEARImportDataModel() {
		return (EARImportDataModel) model;
	}

	public boolean canModify(Object element, String property) {
		return !getEARImportDataModel().getBooleanProperty(J2EEImportDataModel.PRESERVE_PROJECT_METADATA);
	}

	public java.lang.Object getValue(java.lang.Object element, java.lang.String property) {
		TableItem[] items = earFileListViewer.getTable().getSelection();
		TableItem item = items[0];
		return item.getText(1);
	}

	public void modify(Object element, String property, Object value) {
		TableItem elementHolder = (TableItem) element;
		if (property.equals(PROJECT_COLUMN)) {
			elementHolder.setText(1, (String) value);
			((J2EEImportDataModel) elementHolder.getData()).setProperty(J2EEImportDataModel.PROJECT_NAME, value);
		}
	}

	protected void restoreWidgetValues() {
		// This page doesn't implement...
	}

	public void storeDefaultSettings() {
		// This page doesn't implement...
	}

	protected String[] getValidationPropertyNames() {
		return new String[]{EARImportDataModel.NESTED_PROJECTS_VALIDATION, EARImportDataModel.OVERWRITE_NESTED_PROJECTS, EARImportDataModel.SELECTED_MODELS_LIST};
	}
}