/** * Copyright (c) 2016 Codetrails GmbH. * 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: * Johannes Dorn - initial API and implementation. */ package org.eclipse.recommenders.internal.models.rcp; import static org.eclipse.recommenders.internal.models.rcp.Constants.PREF_REPOSITORY_URL_LIST; import java.net.URI; import java.util.List; import org.eclipse.jface.dialogs.IDialogConstants; import org.eclipse.jface.layout.GridDataFactory; import org.eclipse.jface.layout.GridLayoutFactory; import org.eclipse.jface.preference.FieldEditor; import org.eclipse.jface.viewers.ArrayContentProvider; import org.eclipse.jface.viewers.ColumnLabelProvider; import org.eclipse.jface.viewers.TableViewer; import org.eclipse.jface.window.Window; import org.eclipse.recommenders.internal.models.rcp.l10n.Messages; import org.eclipse.recommenders.rcp.SharedImages; import org.eclipse.recommenders.utils.Uris; import org.eclipse.swt.SWT; import org.eclipse.swt.events.MouseAdapter; import org.eclipse.swt.events.MouseEvent; import org.eclipse.swt.events.SelectionAdapter; import org.eclipse.swt.events.SelectionEvent; import org.eclipse.swt.graphics.Image; import org.eclipse.swt.graphics.Point; import org.eclipse.swt.graphics.Rectangle; import org.eclipse.swt.widgets.Button; import org.eclipse.swt.widgets.Composite; import org.eclipse.swt.widgets.Control; import org.eclipse.swt.widgets.TableItem; import com.google.common.collect.Lists; public class ModelRepositoriesFieldEditor extends FieldEditor { private TableViewer tableViewer; private Composite buttonBox; private Button addButton; private Button editButton; private Button removeButton; private Button upButton; private Button downButton; private final ModelsRcpPreferences preferences; private final SharedImages images; public ModelRepositoriesFieldEditor(String name, Composite parent, ModelsRcpPreferences preferences, SharedImages images) { super(name, Messages.FIELD_LABEL_REPOSITORY_URIS, parent); this.preferences = preferences; this.images = images; } @Override protected void adjustForNumColumns(int numColumns) { } @Override protected void doFillIntoGrid(Composite parent, int numColumns) { Control control = getLabelControl(parent); GridDataFactory.swtDefaults().span(numColumns, 1).applyTo(control); tableViewer = getTableControl(parent); GridDataFactory.fillDefaults().align(SWT.FILL, SWT.FILL).span(numColumns - 1, 1).grab(true, true) .applyTo(tableViewer.getTable()); buttonBox = getButtonControl(parent); updateButtonStatus(); GridDataFactory.fillDefaults().align(SWT.FILL, SWT.BEGINNING).applyTo(buttonBox); } private TableViewer getTableControl(Composite parent) { final TableViewer tableViewer = new TableViewer(parent, SWT.BORDER | SWT.FULL_SELECTION); tableViewer.setContentProvider(new ArrayContentProvider()); tableViewer.setLabelProvider(new ColumnLabelProvider() { @Override public String getText(Object element) { String repositoryUrl = (String) element; URI uri = Uris.parseURI(repositoryUrl).orNull(); if (uri == null) { return repositoryUrl; } return Uris.toStringWithMaskedPassword(uri, '*'); } @Override public Image getImage(Object element) { String repositoryUrl = (String) element; URI uri = Uris.parseURI(repositoryUrl).orNull(); if (uri == null) { return images.getImage(SharedImages.Images.OBJ_REPOSITORY); } else if (Uris.isPasswordProtected(uri)) { return images.getImage(SharedImages.Images.OBJ_LOCKED_REPOSITORY); } else if (preferences.hasPassword(repositoryUrl)) { return images.getImage(SharedImages.Images.OBJ_LOCKED_REPOSITORY); } else { return images.getImage(SharedImages.Images.OBJ_REPOSITORY); } } }); tableViewer.getTable().addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { updateButtonStatus(); } }); tableViewer.getTable().addMouseListener(new MouseAdapter() { @Override public void mouseDoubleClick(MouseEvent e) { TableItem item = tableViewer.getTable().getItem(new Point(e.x, e.y)); if (item == null) { return; } Rectangle bounds = item.getBounds(); boolean isClickOnCheckbox = e.x < bounds.x; if (isClickOnCheckbox) { return; } String selectedRepository = getSelectedRepository(); editRepository(selectedRepository); updateButtonStatus(); } }); return tableViewer; } private Composite getButtonControl(Composite parent) { Composite box = new Composite(parent, SWT.NONE); GridLayoutFactory.fillDefaults().applyTo(box); addButton = createButton(box, Messages.PREFPAGE_BUTTON_ADD); addButton.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { addNewRepository(); updateButtonStatus(); } }); editButton = createButton(box, Messages.PREFPAGE_BUTTON_EDIT); editButton.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { editRepository(getSelectedRepository()); updateButtonStatus(); } }); editButton.setEnabled(false); removeButton = createButton(box, Messages.PREFPAGE_BUTTON_REMOVE); removeButton.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { removeRepository(getSelectedRepository()); updateButtonStatus(); } }); upButton = createButton(box, Messages.PREFPAGE_BUTTON_UP); upButton.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { moveRepositoryUp(getSelectedRepository()); updateButtonStatus(); } }); downButton = createButton(box, Messages.PREFPAGE_BUTTON_DOWN); downButton.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { moveRepositoryDown(getSelectedRepository()); updateButtonStatus(); } }); return box; } private String getSelectedRepository() { List<String> tableInput = getTableViewerInput(); if (tableInput == null) { return null; } int index = tableViewer.getTable().getSelectionIndex(); if (index < 0) { return null; } return tableInput.get(index); } private List<String> getTableViewerInput() { return (List<String>) tableViewer.getInput(); } private void updateButtonStatus() { int selectionIndex = tableViewer.getTable().getSelectionIndex(); String selectedRepository = getSelectedRepository(); if (selectedRepository == null) { editButton.setEnabled(false); removeButton.setEnabled(false); upButton.setEnabled(false); downButton.setEnabled(false); return; } editButton.setEnabled(true); removeButton.setEnabled(true); upButton.setEnabled(selectionIndex > 0); downButton.setEnabled(selectionIndex < tableViewer.getTable().getItemCount() - 1); } private void removeRepository(String selectedRepository) { List<String> list = getTableViewerInput(); list.remove(selectedRepository); tableViewer.refresh(); } private void addNewRepository() { RepositoryDetailsDialog newRepositoryDialog = new RepositoryDetailsDialog(null, null, getTableViewerInput(), preferences); if (newRepositoryDialog.open() == Window.OK) { String newRepositoryUrl = newRepositoryDialog.getRepositoryUrl(); List<String> list = getTableViewerInput(); list.add(newRepositoryUrl); tableViewer.refresh(); } } private void editRepository(String selectedRepository) { RepositoryDetailsDialog editRepositoryDialog = new RepositoryDetailsDialog(null, selectedRepository, getTableViewerInput(), preferences); if (editRepositoryDialog.open() == Window.OK) { String updatedRepositoryUrl = editRepositoryDialog.getRepositoryUrl(); List<String> list = getTableViewerInput(); int indexOfOriginalRepository = list.indexOf(selectedRepository); list.remove(indexOfOriginalRepository); list.add(indexOfOriginalRepository, updatedRepositoryUrl); tableViewer.refresh(); } } private void moveRepositoryUp(String selectedRepository) { List<String> list = getTableViewerInput(); int indexOfRepository = list.indexOf(selectedRepository); list.remove(indexOfRepository); list.add(indexOfRepository - 1, selectedRepository); tableViewer.refresh(); } private void moveRepositoryDown(String selectedRepository) { List<String> list = getTableViewerInput(); int indexOfRepository = list.indexOf(selectedRepository); list.remove(indexOfRepository); list.add(indexOfRepository + 1, selectedRepository); tableViewer.refresh(); } private Button createButton(Composite box, String text) { Button button = new Button(box, SWT.PUSH); button.setText(text); int widthHint = Math.max(convertHorizontalDLUsToPixels(button, IDialogConstants.BUTTON_WIDTH), button.computeSize(SWT.DEFAULT, SWT.DEFAULT, true).x); GridDataFactory.swtDefaults().align(SWT.FILL, SWT.CENTER).hint(widthHint, SWT.DEFAULT).applyTo(button); return button; } @Override protected void doLoad() { tableViewer.setInput(Lists.newArrayList(preferences.remotes)); } @Override protected void doLoadDefault() { String defaultRemotes = getPreferenceStore().getDefaultString(PREF_REPOSITORY_URL_LIST); tableViewer.setInput(Lists.newArrayList(ModelsRcpPreferences.splitRemoteRepositoryString(defaultRemotes))); } @Override protected void doStore() { List<String> repositories = getTableViewerInput(); getPreferenceStore().setValue(PREF_REPOSITORY_URL_LIST, ModelsRcpPreferences.joinRemoteRepositoriesToString(repositories)); } @Override public int getNumberOfControls() { return 2; } }