diff options
Diffstat (limited to 'bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/ConfigureRepositoryLocationsTable.java')
-rw-r--r-- | bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/ConfigureRepositoryLocationsTable.java | 488 |
1 files changed, 488 insertions, 0 deletions
diff --git a/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/ConfigureRepositoryLocationsTable.java b/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/ConfigureRepositoryLocationsTable.java new file mode 100644 index 000000000..c59281ec6 --- /dev/null +++ b/bundles/org.eclipse.team.cvs.ui/src/org/eclipse/team/internal/ccvs/ui/ConfigureRepositoryLocationsTable.java @@ -0,0 +1,488 @@ +/******************************************************************************* + * 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]); + } + +} |