blob: 5882ebd5205b375630977c4a5160cb79b96174e7 [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2010-2015 Nokia Siemens Networks Oyj, Finland.
*
* This program and the accompanying materials
* are made available under the terms of the Eclipse Public License 2.0
* which accompanies this distribution, and is available at
* https://www.eclipse.org/legal/epl-2.0/
*
* SPDX-License-Identifier: EPL-2.0
*
* Contributors:
* Nokia Siemens Networks - initial implementation
* Petri Tuononen - Initial implementation
*******************************************************************************/
package org.eclipse.cdt.managedbuilder.llvm.ui.preferences;
import java.util.regex.Pattern;
import org.eclipse.cdt.managedbuilder.llvm.util.Separators;
import org.eclipse.core.runtime.Assert;
import org.eclipse.jface.dialogs.IDialogConstants;
import org.eclipse.jface.preference.ListEditor;
import org.eclipse.jface.resource.JFaceResources;
import org.eclipse.swt.SWT;
import org.eclipse.swt.events.DisposeEvent;
import org.eclipse.swt.events.DisposeListener;
import org.eclipse.swt.events.SelectionAdapter;
import org.eclipse.swt.events.SelectionEvent;
import org.eclipse.swt.events.SelectionListener;
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.List;
import org.eclipse.swt.widgets.Shell;
import org.eclipse.swt.widgets.Widget;
/**
* An abstract list editor that manages a list of input values.
* The editor displays a list containing the values, buttons for adding and removing
* values, and Up and Down buttons to adjust the order of elements in the list.
*
*/
public abstract class LlvmListEditor extends ListEditor {
/**
* The list widget; <code>null</code> if none
* (before creation or after disposal).
*/
List list;
/**
* The button box containing the Add, Remove, Up, and Down buttons;
* <code>null</code> if none (before creation or after disposal).
*/
Composite buttonBox;
/**
* The Add button.
*/
Button addButton;
/**
* The Remove button.
*/
Button removeButton;
/**
* The Up button.
*/
Button upButton;
/**
* The Down button.
*/
Button downButton;
/**
* The selection listener.
*/
private SelectionListener selectionListener;
/**
* Creates a list field editor.
*
* @param name the name of the preference this field editor works on
* @param labelText the label text of the field editor
* @param parent the parent of the field editor's control
*/
protected LlvmListEditor(String name, String labelText, Composite parent) {
super(name, labelText, parent);
}
@Override
/**
* Combines the given list of items into a single String.
* This method is the converse of parseString.
*/
protected String createList(String[] items) {
StringBuilder stringBuilder = new StringBuilder();
for (String item : items) {
if (stringBuilder.length() > 0) {
stringBuilder.append(Separators.getPathSeparator());
}
stringBuilder.append(item);
}
return stringBuilder.toString();
}
@Override
/** Splits the given String into a list of Strings.
* This method is the converse of createList.
*/
protected String[] parseString(String stringList) {
if (stringList != null && stringList.length() > 0) {
return stringList.split(Pattern.quote(Separators.getPathSeparator()));
}
return new String[0];
}
/**
* Creates the Add, Remove, Up, and Down button in the given button box.
*
* @param box the box for the buttons
*/
private void createButtons(Composite box) {
this.addButton = createPushButton(box, "ListEditor.add");//$NON-NLS-1$
this.removeButton = createPushButton(box, "ListEditor.remove");//$NON-NLS-1$
this.upButton = createPushButton(box, "ListEditor.up");//$NON-NLS-1$
this.downButton = createPushButton(box, "ListEditor.down");//$NON-NLS-1$
}
/**
* Helper method to create a push button.
*
* @param parent the parent control
* @param key the resource name used to supply the button's label text
* @return Button
*/
private Button createPushButton(Composite parent, String key) {
Button button = new Button(parent, SWT.PUSH);
button.setText(JFaceResources.getString(key));
button.setFont(parent.getFont());
GridData data = new GridData(GridData.FILL_HORIZONTAL);
int widthHint = convertHorizontalDLUsToPixels(button, IDialogConstants.BUTTON_WIDTH);
data.widthHint = Math.max(widthHint, button.computeSize(SWT.DEFAULT, SWT.DEFAULT, true).x);
button.setLayoutData(data);
button.addSelectionListener(getSelectionListener());
return button;
}
/**
* Creates a selection listener.
*/
@Override
public void createSelectionListener() {
this.selectionListener = new SelectionAdapter() {
@Override
public void widgetSelected(SelectionEvent event) {
Widget widget = event.widget;
if (widget == LlvmListEditor.this.addButton) {
addPressed();
} else if (widget == LlvmListEditor.this.removeButton) {
removePressed();
} else if (widget == LlvmListEditor.this.upButton) {
upPressed();
} else if (widget == LlvmListEditor.this.downButton) {
downPressed();
} else if (widget == LlvmListEditor.this.list) {
selectionChanged();
}
}
};
}
/**
* Returns this field editor's button box containing the Add, Remove,
* Up, and Down button.
*
* @param parent the parent control
* @return the button box
*/
@Override
public Composite getButtonBoxControl(Composite parent) {
if (this.buttonBox == null) {
this.buttonBox = new Composite(parent, SWT.NULL);
GridLayout layout = new GridLayout();
layout.marginWidth = 0;
this.buttonBox.setLayout(layout);
createButtons(this.buttonBox);
this.buttonBox.addDisposeListener(new DisposeListener() {
@Override
public void widgetDisposed(DisposeEvent event) {
LlvmListEditor.this.addButton = null;
LlvmListEditor.this.removeButton = null;
LlvmListEditor.this.upButton = null;
LlvmListEditor.this.downButton = null;
LlvmListEditor.this.buttonBox = null;
}
});
} else {
checkParent(this.buttonBox, parent);
}
selectionChanged();
return this.buttonBox;
}
/**
* Returns this field editor's list control.
*
* @param parent the parent control
* @return the list control
*/
@Override
public List getListControl(Composite parent) {
if (this.list == null) {
this.list = new List(parent, SWT.BORDER | SWT.MULTI | SWT.V_SCROLL | SWT.H_SCROLL);
this.list.setFont(parent.getFont());
this.list.addSelectionListener(getSelectionListener());
this.list.addDisposeListener(new DisposeListener() {
@Override
public void widgetDisposed(DisposeEvent event) {
LlvmListEditor.this.list = null;
}
});
} else {
checkParent(this.list, parent);
}
return this.list;
}
/**
* Returns this field editor's selection listener. The listener is created if nessessary.
* @return the selection listener
*/
private SelectionListener getSelectionListener() {
if (this.selectionListener == null) {
createSelectionListener();
}
return this.selectionListener;
}
/**
* Invoked when the selection in the list has changed.
*
* <p>
* The default implementation of this method utilizes the selection index
* and the size of the list to toggle the enablement of the up, down and
* remove buttons.
* </p>
*
*/
@Override
protected void selectionChanged() {
int index = this.list.getSelectionIndex();
int size = this.list.getItemCount();
this.removeButton.setEnabled(index >= 0);
this.upButton.setEnabled(size > 1 && index > 0);
this.downButton.setEnabled(size > 1 && index >= 0 && index < size - 1);
}
/**
* Moves the currently selected item up or down.
*
* @param up <code>true</code> if the item should move up,
* and <code>false</code> if it should move down
*/
private void swap(boolean up) {
setPresentsDefaultValue(false);
int index = this.list.getSelectionIndex();
int target = up ? index - 1 : index + 1;
if (index >= 0) {
String[] selection = this.list.getSelection();
Assert.isTrue(selection.length == 1);
this.list.remove(index);
this.list.add(selection[0], target);
this.list.setSelection(target);
}
selectionChanged();
}
/**
* Returns this field editor's shell.
* <p>
* This method is internal to the framework; subclasses should not call
* this method.
* </p>
*
* @return the shell
*/
@Override
protected Shell getShell() {
if (this.addButton == null) {
return null;
}
return this.addButton.getShell();
}
/**
* Notifies that the Add button has been pressed.
*/
void addPressed() {
setPresentsDefaultValue(false);
String input = getNewInputObject();
if (input != null) {
int index = this.list.getSelectionIndex();
if (index >= 0) {
this.list.add(input, index + 1);
} else {
this.list.add(input, 0);
}
selectionChanged();
}
}
/**
* Notifies that the Remove button has been pressed.
*/
protected abstract void removePressed();
/**
* Notifies that the Up button has been pressed.
*/
void upPressed() {
swap(true);
}
/**
* Notifies that the Down button has been pressed.
*/
void downPressed() {
swap(false);
}
}