/*******************************************************************************
 * Copyright (c) 2007, 2009 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
 *******************************************************************************/

package org.eclipse.team.internal.ccvs.ui;

import java.util.*;
import java.util.List;

import org.eclipse.jface.viewers.*;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.ControlAdapter;
import org.eclipse.swt.events.ControlEvent;
import org.eclipse.swt.graphics.*;
import org.eclipse.swt.widgets.*;
import org.eclipse.team.internal.ccvs.core.CVSRepositoryLocationMatcher;
import org.eclipse.team.internal.ccvs.core.ICVSRepositoryLocation;
import org.eclipse.team.internal.ccvs.core.connection.CVSRepositoryLocation;
import org.eclipse.team.internal.ccvs.core.util.KnownRepositories;

public class ConfigureRepositoryLocationsTable implements ICellModifier,
		IStructuredContentProvider, ITableLabelProvider {

	private static final class AlternativeRepositoryComparator extends
			ViewerComparator {

		public AlternativeRepositoryComparator() {
		}

		private int getCategory(Object element) {
			if (element instanceof RepositoryLocationItem) {
				return 0;
			}
			return 2;
		}

		public int compare(Viewer viewer, Object e1, Object e2) {
			final int compare = getCategory(e1) - getCategory(e2);
			if (compare != 0)
				return compare;
			return super.compare(viewer, ((Item) e1).location,
					((Item) e2).location);
		}
	}

	public abstract static class Item implements Comparable {
		public final ICVSRepositoryLocation location;
		public List alternativeList;
		public int selected;

		public Item(ICVSRepositoryLocation name, List alternative) {
			this.location = name;
			this.alternativeList = alternative;
			this.selected = 0;
		}

		/*
		 * (non-Javadoc)
		 * 
		 * @see java.lang.Comparable#compareTo(java.lang.Object)
		 */
		public int compareTo(Object o) {
			return location.getLocation(false).compareTo(
					((Item) o).location.getLocation(false));
		}
	}

	public static class RepositoryLocationItem extends Item {
		public RepositoryLocationItem(
				ICVSRepositoryLocation projectSetRepositoryLocation,
				List suggestedRepositoryLocations) {
			super(projectSetRepositoryLocation, suggestedRepositoryLocations);
		}
	}

	protected static final String ITEM = "item"; //$NON-NLS-1$
	protected static final String PROPERTY_ALTERNATIVE_LIST = "alternativeList"; //$NON-NLS-1$

	private TableViewer fTableViewer;

	private CellEditor[] cellEditors;

	private TextCellEditor dummyAlternativeRepositoryEditor;

	private Table table;

	/**
	 * List of <code>AlternativeRepositoryTable.RepositoryLocationItem</code>
	 * used as an input to the table.
	 */
	private List fAlternatives;

	private boolean fShowOnlyCompatibeLocations = true;

	public ConfigureRepositoryLocationsTable(Map alternativesMap) {
		fAlternatives = new ArrayList();
		for (Iterator iterator = alternativesMap.entrySet().iterator(); iterator
				.hasNext();) {
			Map.Entry entry = (Map.Entry) iterator.next();
			fAlternatives
					.add(new ConfigureRepositoryLocationsTable.RepositoryLocationItem(
							(ICVSRepositoryLocation) entry.getKey(),
							(List) entry.getValue()));
		}
	}

	public Composite createControl(final Composite composite) {
		/**
		 * Create a table.
		 */
		table = new Table(composite, SWT.V_SCROLL | SWT.BORDER | SWT.MULTI
				| SWT.FULL_SELECTION);
		// table.setLayoutData(SWTUtils.createHVFillGridData());
		table.setLinesVisible(true);
		table.setHeaderVisible(true);
		table.addListener(SWT.MeasureItem, new Listener() {
			public void handleEvent(Event event) {
				// int clientWidth = table.getClientArea().width;
				event.height = event.gc.getFontMetrics().getHeight() + 5;
				// event.width = clientWidth * 2;
			}
		});

		/**
		 * The 'Project set repository location' column
		 */
		final TableColumn projectSetRepositoryColumn = new TableColumn(table,
				SWT.NONE, 0);
		projectSetRepositoryColumn
				.setText(CVSUIMessages.ConfigureRepositoryLocationsWizard_column0);

		/**
		 * The 'Repository location' column
		 */
		final TableColumn alternativeRepositoryColums = new TableColumn(table,
				SWT.NONE, 1);
		alternativeRepositoryColums
				.setText(CVSUIMessages.ConfigureRepositoryLocationsWizard_column1);

		composite.addControlListener(new ControlAdapter() {
			public void controlResized(ControlEvent e) {
				Rectangle area = composite.getClientArea();
				Point size = table.computeSize(SWT.DEFAULT, SWT.DEFAULT);
				ScrollBar vBar = table.getVerticalBar();
				int width = area.width - table.computeTrim(0, 0, 0, 0).width
						- vBar.getSize().x;
				if (size.y > area.height + table.getHeaderHeight()) {
					// Subtract the scrollbar width from the total column width
					// if a vertical scrollbar will be required
					Point vBarSize = vBar.getSize();
					width -= vBarSize.x;
				}
				Point oldSize = table.getSize();
				if (oldSize.x > area.width) {
					// table is getting smaller so make the columns
					// smaller first and then resize the table to
					// match the client area width
					projectSetRepositoryColumn.setWidth(width / 2);
					alternativeRepositoryColums.setWidth(width
							- projectSetRepositoryColumn.getWidth());
					table.setSize(area.width, area.height);
				} else {
					// table is getting bigger so make the table
					// bigger first and then make the columns wider
					// to match the client area width
					table.setSize(area.width, area.height);
					projectSetRepositoryColumn.setWidth(width / 2);
					alternativeRepositoryColums.setWidth(width
							- projectSetRepositoryColumn.getWidth());
				}
			}
		});

		/**
		 * Create a viewer for the table.
		 */
		fTableViewer = new TableViewer(table);
		fTableViewer.setContentProvider(this);
		fTableViewer.setLabelProvider(this);
		fTableViewer.setComparator(new AlternativeRepositoryComparator());
		
		/**
		 * Add a cell editor in the 'Repository location' column
		 */
		TableViewerFocusCellManager focusCellManager = new TableViewerFocusCellManager(
				fTableViewer, new FocusCellOwnerDrawHighlighter(fTableViewer));
		ColumnViewerEditorActivationStrategy editorActivationStrategy = new ColumnViewerEditorActivationStrategy(
				fTableViewer) {
			protected boolean isEditorActivationEvent(
					ColumnViewerEditorActivationEvent event) {
				return event.eventType == ColumnViewerEditorActivationEvent.MOUSE_DOUBLE_CLICK_SELECTION
						|| (event.eventType == ColumnViewerEditorActivationEvent.KEY_PRESSED && event.keyCode == SWT.F2);
			}
		};
		TableViewerEditor.create(fTableViewer, focusCellManager,
				editorActivationStrategy, ColumnViewerEditor.DEFAULT
						| ColumnViewerEditor.KEYBOARD_ACTIVATION);

		cellEditors = new CellEditor[2];
		cellEditors[0] = null;
		// to enable cell editing, create a dummy cell editor
		cellEditors[1] = dummyAlternativeRepositoryEditor = new TextCellEditor(
				table, SWT.READ_ONLY);

		fTableViewer.setCellEditors(cellEditors);
		fTableViewer.setColumnProperties(new String[] { ITEM,
				PROPERTY_ALTERNATIVE_LIST });
		fTableViewer.setCellModifier(this);
		fTableViewer.setInput(fAlternatives);
		
		// set initial selection
		for (int i = 0; i < fTableViewer.getTable().getItemCount(); i++) {
			Object element = fTableViewer.getElementAt(i);
			RepositoryLocationItem locationItem = (RepositoryLocationItem) element;
			// select second entry only when it's compatible and the first is
			// unknown (from project set file)
			if (locationItem.alternativeList.size() > 1
					&& !KnownRepositories
							.getInstance()
							.isKnownRepository(
									((ICVSRepositoryLocation) locationItem.alternativeList
											.get(0)).getLocation(false))
					&& CVSRepositoryLocationMatcher
							.isCompatible(
									locationItem.location,
									(ICVSRepositoryLocation) locationItem.alternativeList
											.get(1), false)) {
				locationItem.selected = 1;
			}
		}
		fTableViewer.refresh();
		return table;
	}

	public Object getValue(Object element, String property) {

		final Item item = (Item) element;

		if (PROPERTY_ALTERNATIVE_LIST.equals(property)) {
			return Integer.valueOf(item.selected);
		}
		return null;
	}

	public boolean canModify(Object element, String property) {
		// set the correct cell editor for this element
		cellEditors[1] = getCellEditor(element);
		// only allow modification for editable elements
		return PROPERTY_ALTERNATIVE_LIST.equals(property);
	}

	private CellEditor getCellEditor(Object element) {

		if (element instanceof RepositoryLocationItem) {
			// create combo-box list of alternative repositories
			RepositoryLocationItem item = (RepositoryLocationItem) element;
			
			return new ComboBoxCellEditor(table, getFilteredAlternativeRepositoriesForDisplay(item),
					SWT.READ_ONLY);
		}
		return dummyAlternativeRepositoryEditor;
	}

	public void modify(Object element, String property, Object value) {

		final IStructuredSelection selection = (IStructuredSelection) fTableViewer
				.getSelection();
		final Item item = (Item) selection.getFirstElement();
		if (item == null)
			return;

		final int comboIndex = ((Integer) value).intValue();

		if (PROPERTY_ALTERNATIVE_LIST.equals(property)) {
			item.selected = comboIndex;
		}
		fTableViewer.refresh(item);
	}

	public Image getColumnImage(Object element, int columnIndex) {
		return null;
	}

	public String getColumnText(Object element, int columnIndex) {
		final Item item = (Item) element;

		switch (columnIndex) {
		case 0:
			return item.location.getLocation(false);
		case 1: 
			return getFilteredAlternativeRepositoriesForDisplay(item)[item.selected];
		default:
			return null;
		}
	}

	public void addListener(ILabelProviderListener listener) {
	}

	public void dispose() {
	}

	public boolean isLabelProperty(Object element, String property) {
		return false;
	}

	public void removeListener(ILabelProviderListener listener) {
	}

	public Object[] getElements(Object inputElement) {
		return ((Collection) inputElement).toArray();
	}

	public void inputChanged(Viewer viewer, Object oldInput, Object newInput) {
	}

	public IStructuredSelection getSelection() {
		return (IStructuredSelection) fTableViewer.getSelection();
	}

	public TableViewer getViewer() {
		return fTableViewer;
	}

	/**
	 * @return a selected (in a combo box) alternative repository location for
	 *         the first selected element
	 */
	public CVSRepositoryLocation getSelectedAlternativeRepository() {
		RepositoryLocationItem firstElement = (RepositoryLocationItem) getSelection()
				.getFirstElement();
		return (CVSRepositoryLocation) getFilteredAlternativeRepositories(firstElement)
				.get(firstElement.selected);
	}

	/**
	 * Add newly created repository location to all RepositoryLocationItems. The
	 * location is added at the end of a list. For selected and compatible rows
	 * it will be automatically selected.
	 * 
	 * @param location
	 *            Location to add.
	 */
	void addAlternativeRepository(ICVSRepositoryLocation location) {
		for (int i = 0; i < fTableViewer.getTable().getItemCount(); i++) {
			Object element = fTableViewer.getElementAt(i);
			RepositoryLocationItem rli = (RepositoryLocationItem) element;
			// TODO: at this moment a newly created repository location
			// is added at the end of every locationItem, we could
			// consider sorting the list again
			rli.alternativeList.add(location);
			if (getSelection().toList().contains(element)
					&& CVSRepositoryLocationMatcher.isCompatible(location,
							rli.location, false)) {
				// at the end
				rli.selected = getFilteredAlternativeRepositories(rli).size() - 1;
			}
		}
		fTableViewer.refresh(true);
	}

	/**
	 * @return A map with repository location from the project set as a key and
	 *         selected repository location from a combo box as value.
	 */
	public Map getSelected() {
		Map map = new HashMap();
		for (Iterator iterator = fAlternatives.iterator(); iterator.hasNext();) {
			RepositoryLocationItem rli = (RepositoryLocationItem) iterator
					.next();
			map.put(rli.location, getFilteredAlternativeRepositories(rli).get(rli.selected));
		}
		return map;
	}

	/**
	 * Change the fShowOnlyCompatibeLocations flag. If set to <code>true</code>
	 * only compatible repository locations are shown, current selection will be
	 * updated when a non-compatible entry is selected. If set to
	 * <code>false</code> all repository locations are shown, current
	 * selection will be updated if necessary.
	 * 
	 * @param show
	 *            The flag
	 */
	public void setShowOnlyCompatibleLocations(boolean show) {
		fShowOnlyCompatibeLocations = show;
		for (int i = 0; i < fTableViewer.getTable().getItemCount(); i++) {
			Object element = fTableViewer.getElementAt(i);
			RepositoryLocationItem rli = (RepositoryLocationItem) element;
			updateSelection(rli); 
		}
		fTableViewer.refresh(true);
	}
	
	private List getFilteredAlternativeRepositories(Item item) {
		return getFilteredAlternativeRepositories(item, fShowOnlyCompatibeLocations);
	}
	
	private List getFilteredAlternativeRepositories(Item item, boolean showOnlyCompatible) {
		List alternativeList = item.alternativeList;
		if (!showOnlyCompatible) {
			return alternativeList;
		} else {
			List alternativeFiltered = new ArrayList();
			for (int i = 0; i < alternativeList.size(); i++) {
				CVSRepositoryLocation repo = (CVSRepositoryLocation) alternativeList.get(i);
				// If "Show only compatible..." option is on add only compatible
				// locations or the location itself
				if (!CVSRepositoryLocationMatcher.isCompatible(item.location,
						repo, true)){
					continue; // skip this repo location
				}
				alternativeFiltered.add(repo);
			}
			return alternativeFiltered;
		}
	}
	
	private void updateSelection(Item item) {
		if (fShowOnlyCompatibeLocations) {
			int shift = 0;
			for (int j = 0; j <= item.selected; j++) {
				ICVSRepositoryLocation rl = (ICVSRepositoryLocation) item.alternativeList
						.get(j);
				if (!CVSRepositoryLocationMatcher.isCompatible(item.location,
						rl, true)) {
					shift++;
				}
			}
			item.selected -= shift;

			// the selected location is neither compatible nor equal to the
			// one from the project set
			ICVSRepositoryLocation selected = (ICVSRepositoryLocation) getFilteredAlternativeRepositories(
					item).get(item.selected);
			if (!CVSRepositoryLocationMatcher.isCompatible(item.location,
					selected, true)) {
				item.selected = 0; // default
				// find compatible
				for (int j = 0; j < item.alternativeList.size(); j++) {
					ICVSRepositoryLocation l = (ICVSRepositoryLocation) item.alternativeList
							.get(j);
					if (CVSRepositoryLocationMatcher.isCompatible(l,
							item.location, true)) {
						item.selected = j;
						break;
					}
				}
			}
		} else {
			// show all
			int shift = 0;
			// index of (item.)selected object from the full list
			for (int j = 0; j <= getFilteredAlternativeRepositories(item)
					.indexOf(
							getFilteredAlternativeRepositories(item, true).get(
									item.selected)); j++) {
				ICVSRepositoryLocation rl = (ICVSRepositoryLocation) item.alternativeList
						.get(j);
				if (!CVSRepositoryLocationMatcher.isCompatible(item.location, rl,
						true)) {
					shift++;
				}
			}
			item.selected += shift;
		}
	}
	
	private String[] getFilteredAlternativeRepositoriesForDisplay(Item item) {
		List filteredAlternativeList = getFilteredAlternativeRepositories(item);
		List repositoriesForDisplay = new ArrayList();
		for (int i = 0; i < filteredAlternativeList.size(); i++) {
			CVSRepositoryLocation rl = (CVSRepositoryLocation) filteredAlternativeList
					.get(i);
			repositoriesForDisplay.add(rl.getLocation());
		}
		return (String[]) repositoriesForDisplay.toArray(new String[0]);
	}

}
