| /******************************************************************************* |
| * 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 |
| *******************************************************************************/ |
| |
| package org.eclipse.jst.ws.internal.consumption.ui.wsil; |
| |
| import java.util.ArrayList; |
| import java.util.List; |
| |
| import org.eclipse.jface.viewers.ColumnWeightData; |
| import org.eclipse.jface.viewers.ILabelProviderListener; |
| import org.eclipse.jface.viewers.ISelection; |
| import org.eclipse.jface.viewers.ISelectionChangedListener; |
| import org.eclipse.jface.viewers.IStructuredContentProvider; |
| import org.eclipse.jface.viewers.IStructuredSelection; |
| import org.eclipse.jface.viewers.ITableLabelProvider; |
| import org.eclipse.jface.viewers.SelectionChangedEvent; |
| import org.eclipse.jface.viewers.StructuredSelection; |
| import org.eclipse.jface.viewers.TableLayout; |
| import org.eclipse.jface.viewers.TableViewer; |
| import org.eclipse.jface.viewers.Viewer; |
| import org.eclipse.jst.ws.internal.consumption.ui.plugin.WebServiceConsumptionUIPlugin; |
| import org.eclipse.swt.SWT; |
| import org.eclipse.swt.custom.TableEditor; |
| import org.eclipse.swt.events.KeyEvent; |
| import org.eclipse.swt.events.KeyListener; |
| import org.eclipse.swt.events.MouseEvent; |
| import org.eclipse.swt.events.MouseListener; |
| import org.eclipse.swt.events.SelectionEvent; |
| import org.eclipse.swt.events.SelectionListener; |
| import org.eclipse.swt.events.TraverseEvent; |
| import org.eclipse.swt.events.TraverseListener; |
| import org.eclipse.swt.graphics.Image; |
| import org.eclipse.swt.graphics.Rectangle; |
| 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.swt.widgets.Text; |
| import org.eclipse.ui.PlatformUI; |
| |
| |
| public class TableViewerEditor extends Composite |
| { |
| private int DEFAULT_TABLE_HEIGHT_HINT = 100; |
| private int DEFAULT_COLUMN_WIDTH = 80; |
| |
| private String[] columns_; |
| private TableViewer tableViewer_; |
| private Table table_; |
| private TableEditor editor_; |
| private TableEditorListener tableEditorListener_; |
| private Text text_; |
| private Button add_; |
| private Button remove_; |
| |
| private List values_; |
| private Object defaultValue_; |
| |
| public TableViewerEditor(Composite parent, String[] columns, List initValues, Object defaultValue) |
| { |
| super(parent, SWT.NONE); |
| columns_ = columns; |
| values_ = new ArrayList(); |
| if (initValues != null && initValues.size() > 0) |
| values_.addAll(initValues); |
| defaultValue_ = (defaultValue != null) ? defaultValue : new String(""); |
| createPartControl(this); |
| } |
| |
| private void createPartControl(Composite parent) |
| { |
| GridLayout gl = new GridLayout(); |
| gl.marginHeight = 0; |
| gl.marginWidth = 0; |
| setLayout(gl); |
| setLayoutData(new GridData(GridData.FILL_HORIZONTAL)); |
| |
| Composite composite = new Composite(parent, SWT.NONE); |
| gl = new GridLayout(); |
| gl.marginHeight = 0; |
| gl.marginWidth = 0; |
| composite.setLayout(gl); |
| composite.setLayoutData(new GridData(GridData.FILL_HORIZONTAL)); |
| |
| table_ = new Table(composite, SWT.SINGLE | SWT.FULL_SELECTION | SWT.BORDER); |
| GridData gd = new GridData(GridData.FILL_BOTH); |
| gd.heightHint = DEFAULT_TABLE_HEIGHT_HINT; |
| table_.setLayoutData(gd); |
| table_.setHeaderVisible(true); |
| table_.setLinesVisible(true); |
| TableLayout tableLayout = new TableLayout(); |
| int maxWidth = DEFAULT_COLUMN_WIDTH; |
| for (int i = 0; i < columns_.length; i++) |
| { |
| TableColumn tableColumn = new TableColumn(table_, SWT.NONE); |
| tableColumn.setText(columns_[i]); |
| tableColumn.pack(); |
| int tableColumnWidth = Math.max(DEFAULT_COLUMN_WIDTH, tableColumn.getWidth()); |
| maxWidth = Math.max(maxWidth, tableColumnWidth); |
| ColumnWeightData columnData = new ColumnWeightData(tableColumnWidth, tableColumnWidth, true); |
| tableLayout.addColumnData(columnData); |
| } |
| table_.setLayout(tableLayout); |
| // initialize the table editor |
| editor_ = new TableEditor(table_); |
| // The editor must have the same size as the cell and must |
| // not be any smaller than 50 pixels. |
| editor_.horizontalAlignment = SWT.LEFT; |
| editor_.grabHorizontal = true; |
| editor_.minimumWidth = maxWidth; |
| tableEditorListener_ = new TableEditorListener(); |
| table_.addMouseListener(tableEditorListener_); |
| tableViewer_ = new TableViewer(table_); |
| tableViewer_.getControl().addKeyListener( |
| new KeyListener() |
| { |
| public void keyPressed(KeyEvent e) |
| { |
| // Del |
| if (((int)e.character) == 127) |
| handleDeleteKeyPressed(); |
| // Enter or space |
| if (((int)e.character) == 13 || ((int)e.character) == 32) |
| tableEditorListener_.editSelection(); |
| } |
| public void keyReleased(KeyEvent e) |
| { |
| } |
| } |
| ); |
| tableViewer_.setContentProvider(new ListContentProvider()); |
| tableViewer_.setLabelProvider(new ListLabelProvider()); |
| tableViewer_.setInput(values_); |
| tableViewer_.addSelectionChangedListener( |
| new ISelectionChangedListener() |
| { |
| public void selectionChanged(SelectionChangedEvent event) |
| { |
| enableRemove(true); |
| } |
| } |
| ); |
| |
| Composite buttonComposite = new Composite(composite, SWT.NONE); |
| gl = new GridLayout(); |
| gl.numColumns = 2; |
| gl.makeColumnsEqualWidth = true; |
| buttonComposite.setLayout(gl); |
| buttonComposite.setLayoutData(new GridData(GridData.GRAB_HORIZONTAL | GridData.HORIZONTAL_ALIGN_BEGINNING)); |
| |
| add_ = new Button(buttonComposite, SWT.PUSH); |
| add_.setText(WebServiceConsumptionUIPlugin.getMessage("%LABEL_ADD")); |
| add_.setLayoutData(new GridData(GridData.HORIZONTAL_ALIGN_FILL)); |
| add_.addSelectionListener( |
| new SelectionListener() |
| { |
| public void widgetSelected(SelectionEvent event) |
| { |
| handleAddButtonSelected(event); |
| } |
| public void widgetDefaultSelected(SelectionEvent event) |
| { |
| } |
| } |
| ); |
| |
| remove_ = new Button(buttonComposite, SWT.PUSH); |
| remove_.setText(WebServiceConsumptionUIPlugin.getMessage("%LABEL_REMOVE")); |
| remove_.setLayoutData(new GridData(GridData.HORIZONTAL_ALIGN_FILL)); |
| remove_.addSelectionListener( |
| new SelectionListener() |
| { |
| public void widgetSelected(SelectionEvent event) |
| { |
| handleRemoveButtonSelected(event); |
| } |
| public void widgetDefaultSelected(SelectionEvent event) |
| { |
| } |
| } |
| ); |
| enableRemove(false); |
| } |
| |
| private void enableRemove(boolean enabled) |
| { |
| remove_.setEnabled(enabled && !tableViewer_.getSelection().isEmpty()); |
| } |
| |
| private void handleAddButtonSelected(SelectionEvent event) |
| { |
| values_.add(defaultValue_); |
| refresh(); |
| setSelectionAsObject(values_.get(table_.getItemCount()-1)); |
| tableEditorListener_.editSelection(); |
| } |
| |
| private void handleRemoveButtonSelected(SelectionEvent event) |
| { |
| handleDeleteKeyPressed(); |
| } |
| |
| private void handleDeleteKeyPressed() |
| { |
| internalDispose(); |
| ISelection selection = tableViewer_.getSelection(); |
| if (selection != null && !selection.isEmpty() && (selection instanceof IStructuredSelection)) |
| { |
| int selectionIndex = table_.getSelectionIndex(); |
| int selectionCount = table_.getItemCount(); |
| values_.remove(selectionIndex); |
| if (selectionIndex < selectionCount-1) |
| setSelectionAsObject(values_.get(selectionIndex)); |
| else if (selectionCount -2 >= 0) |
| setSelectionAsObject(values_.get(selectionCount-2)); |
| refresh(); |
| } |
| } |
| |
| private void internalRefresh() |
| { |
| // synchronize text field, previously selected table cell and model (inputObject) |
| if (text_ != null) |
| { |
| TableItem oldTableItem = editor_.getItem(); |
| int oldColumnIndex = editor_.getColumn(); |
| if (oldTableItem != null && oldColumnIndex >= 0 && oldColumnIndex < columns_.length) |
| { |
| String oldText = text_.getText(); |
| oldTableItem.setText(oldColumnIndex, oldText); |
| int oldRowIndex = table_.indexOf(oldTableItem); |
| values_.set(oldRowIndex, oldText); |
| } |
| } |
| } |
| |
| private void setSelectionAsObject(Object object) |
| { |
| tableViewer_.setSelection(new StructuredSelection(object), true); |
| } |
| |
| public void setToolTipText(String string) |
| { |
| table_.setToolTipText(string); |
| } |
| |
| public void setInfopop(String string) |
| { |
| PlatformUI.getWorkbench().getHelpSystem().setHelp(table_, string); |
| } |
| |
| public void setInput(List list) |
| { |
| values_.clear(); |
| values_.addAll(list); |
| } |
| |
| public void refresh() |
| { |
| internalRefresh(); |
| tableViewer_.refresh(); |
| } |
| |
| public TableItem[] getItems() |
| { |
| internalRefresh(); |
| return table_.getItems(); |
| } |
| |
| public void setEnabled(boolean enabled) |
| { |
| super.setEnabled(enabled); |
| add_.setEnabled(enabled); |
| enableRemove(enabled); |
| } |
| |
| public void dispose() |
| { |
| super.dispose(); |
| internalDispose(); |
| if (editor_ != null) |
| editor_.dispose(); |
| if (table_ != null) |
| table_.dispose(); |
| if (add_ != null) |
| add_.dispose(); |
| if (remove_ != null) |
| remove_.dispose(); |
| } |
| |
| private void internalDispose() |
| { |
| if (text_ != null) |
| text_.dispose(); |
| text_ = null; |
| } |
| |
| protected class TableEditorListener implements MouseListener |
| { |
| private int currSelectionIndex_; |
| private int editRow_; |
| private int editColumn_; |
| |
| public TableEditorListener() |
| { |
| super(); |
| currSelectionIndex_ = -1; |
| editRow_ = -1; |
| editColumn_ = -1; |
| } |
| |
| public void mouseDoubleClick(MouseEvent e) |
| { |
| mouseDown(e); |
| } |
| |
| public void mouseDown(MouseEvent e) |
| { |
| // refresh table |
| internalRefresh(); |
| // Clean up previous text editor control |
| internalDispose(); |
| // update table |
| if (table_.isFocusControl()) |
| { |
| int selectedRowIndex = getSelectedRow(table_, e.y); |
| if (currSelectionIndex_ != -1 && selectedRowIndex != -1 && currSelectionIndex_ == selectedRowIndex) |
| { |
| TableItem tableItem = table_.getItem(selectedRowIndex); |
| int selectedColumnIndex = getSelectedColumn(tableItem, e.x, e.y); |
| if (selectedColumnIndex != -1 && (text_ == null || text_.isDisposed() || selectedColumnIndex != editor_.getColumn())) |
| editSelection(selectedRowIndex, selectedColumnIndex); |
| } |
| currSelectionIndex_ = selectedRowIndex; |
| } |
| } |
| |
| public void mouseUp(MouseEvent e) |
| { |
| } |
| |
| private int getSelectedRow(Table table, int y) |
| { |
| TableItem[] tableItems = table.getItems(); |
| for (int i = 0; i < tableItems.length; i++) |
| { |
| Rectangle rectangle = tableItems[i].getBounds(0); |
| if (rectangle != null && y >= rectangle.y && y < (rectangle.y + rectangle.height)) |
| return i; |
| } |
| return -1; |
| } |
| |
| private int getSelectedColumn(TableItem tableItem, int x, int y) |
| { |
| for (int i = 0; i < columns_.length; i++) |
| { |
| if (tableItem.getBounds(i).contains(x, y)) |
| return i; |
| } |
| return -1; |
| } |
| |
| private void editSelection(int row, int column) |
| { |
| editRow_ = row; |
| editColumn_ = column; |
| TableItem tableItem = table_.getItem(row); |
| // Setup adapter for the new selection |
| text_ = new Text(table_, SWT.NONE); |
| String text = tableItem.getText(column); |
| text_.setText((text != null) ? text : ""); |
| text_.addKeyListener(new KeyListener() |
| { |
| public void keyPressed(KeyEvent e) |
| { |
| // Esc |
| if (((int)e.character) == 27) |
| cancelSelection(); |
| } |
| public void keyReleased(KeyEvent e) |
| { |
| } |
| } |
| ); |
| text_.addTraverseListener(new TraverseListener() |
| { |
| public void keyTraversed(TraverseEvent e) |
| { |
| if (e.detail == SWT.TRAVERSE_TAB_NEXT) |
| traverseTabNext(); |
| else if (e.detail == SWT.TRAVERSE_TAB_PREVIOUS) |
| traverseTabPrevious(); |
| } |
| } |
| ); |
| editor_.setEditor(text_, tableItem, column); |
| text_.setFocus(); |
| text_.selectAll(); |
| } |
| |
| protected void traverseTabNext() |
| { |
| internalRefresh(); |
| internalDispose(); |
| if (!(editRow_ == table_.getItems().length-1 && editColumn_ == columns_.length-1)) |
| { |
| if (editColumn_ < columns_.length-1) |
| editColumn_++; |
| else |
| { |
| editColumn_ = 0; |
| editRow_++; |
| table_.select(editRow_); |
| } |
| editSelection(editRow_, editColumn_); |
| } |
| } |
| |
| protected void traverseTabPrevious() |
| { |
| internalRefresh(); |
| internalDispose(); |
| if (!(editRow_ == 0 && editColumn_ == 0)) |
| { |
| if (editColumn_ > 0) |
| editColumn_--; |
| else |
| { |
| editColumn_ = columns_.length-1; |
| editRow_--; |
| table_.select(editRow_); |
| } |
| editSelection(editRow_, editColumn_); |
| } |
| } |
| |
| public void cancelSelection() |
| { |
| internalDispose(); |
| internalRefresh(); |
| } |
| |
| public void editSelection() |
| { |
| int selectedRowIndex = table_.getSelectionIndex(); |
| if (selectedRowIndex != -1 && columns_.length > 0) |
| { |
| // refresh table |
| internalRefresh(); |
| // Clean up any previous editor control |
| internalDispose(); |
| editSelection(selectedRowIndex, 0); |
| } |
| currSelectionIndex_ = selectedRowIndex; |
| } |
| } |
| |
| protected class ListContentProvider implements IStructuredContentProvider |
| { |
| public void dispose() |
| { |
| } |
| |
| public void inputChanged(Viewer viewer, Object oldInput, Object newInput) |
| { |
| tableViewer_.add(getElements(newInput)); |
| } |
| |
| public Object[] getElements(Object inputElement) |
| { |
| if (inputElement instanceof List) |
| { |
| List list = (List)inputElement; |
| Object[] objects = new Object[list.size()]; |
| for (int i = 0; i < objects.length; i++) |
| objects[i] = list.get(i); |
| return objects; |
| } |
| else |
| return new Object[0]; |
| } |
| } |
| |
| protected class ListLabelProvider implements ITableLabelProvider |
| { |
| public Image getColumnImage(Object element, int columnIndex) |
| { |
| return null; |
| } |
| |
| public String getColumnText(Object element, int columnIndex) |
| { |
| return element.toString(); |
| } |
| |
| public void addListener(ILabelProviderListener listener) |
| { |
| } |
| |
| public void removeListener(ILabelProviderListener listener) |
| { |
| } |
| |
| public boolean isLabelProperty(Object element, String property) |
| { |
| return true; |
| } |
| |
| public void dispose() |
| { |
| } |
| } |
| } |