/******************************************************************************* * Copyright (c) 2009 SpringSource, a divison of VMware, Inc. * 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: * SpringSource, a division of VMware, Inc. - initial API and implementation *******************************************************************************/ package org.eclipse.virgo.ide.bundlor.ui.internal.properties; import java.util.ArrayList; import java.util.Arrays; import java.util.List; import org.eclipse.core.resources.IContainer; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IProject; import org.eclipse.core.resources.IResource; import org.eclipse.core.resources.IWorkspaceRoot; import org.eclipse.core.resources.ResourcesPlugin; import org.eclipse.core.runtime.CoreException; import org.eclipse.jdt.core.JavaCore; import org.eclipse.jdt.ui.JavaElementLabelProvider; import org.eclipse.jdt.ui.JavaElementSorter; import org.eclipse.jface.dialogs.Dialog; import org.eclipse.jface.viewers.ISelectionChangedListener; import org.eclipse.jface.viewers.IStructuredSelection; import org.eclipse.jface.viewers.ITreeContentProvider; import org.eclipse.jface.viewers.LabelProvider; import org.eclipse.jface.viewers.SelectionChangedEvent; import org.eclipse.jface.viewers.TableViewer; import org.eclipse.jface.viewers.Viewer; import org.eclipse.swt.SWT; import org.eclipse.swt.events.SelectionAdapter; import org.eclipse.swt.events.SelectionEvent; import org.eclipse.swt.graphics.Font; import org.eclipse.swt.graphics.Image; 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.Control; import org.eclipse.swt.widgets.Label; import org.eclipse.swt.widgets.Table; import org.eclipse.ui.dialogs.PropertyPage; import org.eclipse.virgo.ide.bundlor.internal.core.BundlorCorePlugin; import org.eclipse.virgo.ide.bundlor.ui.BundlorUiPlugin; import org.springframework.ide.eclipse.core.SpringCorePreferences; import org.springframework.ide.eclipse.ui.SpringUIUtils; import org.springframework.ide.eclipse.ui.dialogs.FilteredElementTreeSelectionDialog; import org.springframework.ide.eclipse.ui.dialogs.StorageSelectionValidator; import org.springframework.util.StringUtils; /** * {@link PropertyPage} to configure properties files for Bundlor variable substitution * @author Christian Dupuis * @author Leo Dos Santos * @since 2.0.0 */ @SuppressWarnings("deprecation") public class BundlorPreferencePage extends PropertyPage { private IProject project; private boolean modified = false; private Table filenameTable; private TableViewer filenamesTableViewer; private Button addButton; private Button deleteButton; private List<String> filenames; private Button scanByteCode; private Button formatManifests; private boolean checkScanByteCodeButton; private boolean checkFormatManifestsButton; protected Control createContents(Composite parent) { Font font = parent.getFont(); Composite parentComposite = new Composite(parent, SWT.NONE); GridLayout layout = new GridLayout(); parentComposite.setLayout(layout); parentComposite.setLayoutData(new GridData(GridData.FILL_HORIZONTAL)); parentComposite.setFont(font); initialize(); scanByteCode = new Button(parentComposite, SWT.CHECK); scanByteCode.setText("Scan output folders instead of source folders to generate MANIFEST.MF"); scanByteCode.setSelection(checkScanByteCodeButton); scanByteCode.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { modified = true; } }); formatManifests = new Button(parentComposite, SWT.CHECK); formatManifests.setText("Auto-format generated MANIFEST.MF and TEST.MF files"); formatManifests.setSelection(checkFormatManifestsButton); formatManifests.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { modified = true; } }); Label description = createDescriptionLabel(parentComposite); description.setLayoutData(new GridData(SWT.FILL, SWT.TOP, true, false)); Composite composite = new Composite(parentComposite, SWT.NONE); layout = new GridLayout(); layout.numColumns = 2; layout.marginHeight = 5; layout.marginWidth = 0; layout.verticalSpacing = 5; layout.horizontalSpacing = 0; composite.setLayout(layout); composite.setLayoutData(new GridData(GridData.FILL_BOTH | GridData.VERTICAL_ALIGN_FILL)); filenameTable = new Table(composite, SWT.SINGLE | SWT.H_SCROLL | SWT.V_SCROLL | SWT.FULL_SELECTION | SWT.BORDER); GridData data = new GridData(GridData.FILL_BOTH); filenameTable.setLayoutData(data); filenamesTableViewer = new TableViewer(filenameTable); filenamesTableViewer.setContentProvider(new PropertiesFileContentProvider()); filenamesTableViewer.setLabelProvider(new FilenameLabelProvider()); filenamesTableViewer.addSelectionChangedListener(new ISelectionChangedListener() { public void selectionChanged(SelectionChangedEvent event) { Object obj = ((IStructuredSelection) event.getSelection()).getFirstElement(); if (obj != null) { deleteButton.setEnabled(true); } else { deleteButton.setEnabled(false); } } }); Composite buttonComposite = new Composite(composite, SWT.NONE); buttonComposite.setLayout(new GridLayout(1, true)); data = new GridData(GridData.VERTICAL_ALIGN_BEGINNING); buttonComposite.setLayoutData(data); addButton = new Button(buttonComposite, SWT.PUSH); addButton.setText("Add"); data = new GridData(); data.widthHint = 100; addButton.setLayoutData(data); addButton.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { FilteredElementTreeSelectionDialog selDialog = new FilteredElementTreeSelectionDialog(SpringUIUtils .getStandardDisplay().getActiveShell(), new JavaElementLabelProvider(), new WorkspaceResourceContentProvider()); selDialog.setTitle("Select properties files"); selDialog .setMessage("Select properties files in the workspace that should be\nused for variable substitution:"); selDialog.setValidator(new StorageSelectionValidator(true)); selDialog.setInput(ResourcesPlugin.getWorkspace().getRoot()); selDialog.setSorter(new JavaElementSorter()); if (selDialog.open() == Dialog.OK) { IResource resource = (IResource) selDialog.getFirstResult(); if (resource instanceof IFile) { if (resource.getProject().equals(project)) { filenames.add(resource.getProjectRelativePath().toString()); } else { filenames.add(resource.getFullPath().toString()); } } modified = true; filenamesTableViewer.setInput(project); } } }); deleteButton = new Button(buttonComposite, SWT.PUSH); deleteButton.setText("Delete"); deleteButton.setLayoutData(data); deleteButton.addSelectionListener(new SelectionAdapter() { @Override public void widgetSelected(SelectionEvent e) { Object selected = ((IStructuredSelection) filenamesTableViewer.getSelection()).getFirstElement(); filenames.remove(selected); filenamesTableViewer.setInput(project); modified = true; } }); filenamesTableViewer.setInput(project); return parentComposite; } private void initialize() { project = (IProject) getElement().getAdapter(IResource.class); noDefaultAndApplyButton(); setDescription("Define properties files that should be used for variable substitution during\ngeneration of MANIFEST.MF file:"); if (project != null) { String properties = SpringCorePreferences.getProjectPreferences(project, BundlorCorePlugin.PLUGIN_ID) .getString(BundlorCorePlugin.TEMPLATE_PROPERTIES_FILE_KEY, BundlorCorePlugin.TEMPLATE_PROPERTIES_FILE_DEFAULT); filenames = new ArrayList<String>(Arrays.asList(org.springframework.util.StringUtils .delimitedListToStringArray(properties, ";"))); checkScanByteCodeButton = SpringCorePreferences.getProjectPreferences(project, BundlorCorePlugin.PLUGIN_ID) .getBoolean(BundlorCorePlugin.TEMPLATE_BYTE_CODE_SCANNING_KEY, BundlorCorePlugin.TEMPLATE_BYTE_CODE_SCANNING_DEFAULT); checkFormatManifestsButton = SpringCorePreferences.getProjectPreferences(project, BundlorCorePlugin.PLUGIN_ID) .getBoolean(BundlorCorePlugin.FORMAT_GENERATED_MANIFESTS_KEY, BundlorCorePlugin.FORMAT_GENERATED_MANIFESTS_DEFAULT); } else { filenames = new ArrayList<String>(); checkScanByteCodeButton = BundlorCorePlugin.TEMPLATE_BYTE_CODE_SCANNING_DEFAULT; checkFormatManifestsButton = BundlorCorePlugin.FORMAT_GENERATED_MANIFESTS_DEFAULT; } } public boolean performOk() { if (!modified) { return true; } SpringCorePreferences.getProjectPreferences(project, BundlorCorePlugin.PLUGIN_ID) .putString(BundlorCorePlugin.TEMPLATE_PROPERTIES_FILE_KEY, StringUtils.collectionToDelimitedString(filenames, ";")); boolean oldScanByteCode = SpringCorePreferences.getProjectPreferences(project, BundlorCorePlugin.PLUGIN_ID) .getBoolean(BundlorCorePlugin.TEMPLATE_BYTE_CODE_SCANNING_KEY, BundlorCorePlugin.TEMPLATE_BYTE_CODE_SCANNING_DEFAULT); SpringCorePreferences.getProjectPreferences(project, BundlorCorePlugin.PLUGIN_ID).putBoolean( BundlorCorePlugin.TEMPLATE_BYTE_CODE_SCANNING_KEY, scanByteCode.getSelection()); SpringCorePreferences.getProjectPreferences(project, BundlorCorePlugin.PLUGIN_ID).putBoolean( BundlorCorePlugin.FORMAT_GENERATED_MANIFESTS_KEY, formatManifests.getSelection()); if (oldScanByteCode != scanByteCode.getSelection()) { BundlorCorePlugin.getDefault().getManifestManager().clearPartialManifest(JavaCore.create(project)); } return true; } class PropertiesFileContentProvider implements ITreeContentProvider { public void dispose() { } public void inputChanged(Viewer viewer, Object oldInput, Object newInput) { } public Object[] getElements(Object inputElement) { if (inputElement instanceof IProject) { return filenames.toArray(); } return new Object[0]; } public Object[] getChildren(Object parentElement) { return getElements(parentElement); } public Object getParent(Object element) { return null; } public boolean hasChildren(Object element) { return getChildren(element).length > 0; } } class FilenameLabelProvider extends LabelProvider { public Image getImage(Object element) { return BundlorUiPlugin.getImage("full/obj16/file_obj.gif"); } public String getText(Object element) { return element.toString(); } } class WorkspaceResourceContentProvider implements ITreeContentProvider { public Object[] getChildren(Object parentElement) { if (parentElement instanceof IContainer) { try { return ((IContainer) parentElement).members(); } catch (CoreException e) { } } return new Object[0]; } public Object getParent(Object element) { if (element instanceof IResource) { return ((IResource) element).getParent(); } return null; } public boolean hasChildren(Object element) { return getChildren(element).length > 0; } public Object[] getElements(Object inputElement) { if (inputElement instanceof IWorkspaceRoot) { List<IProject> projects = new ArrayList<IProject>(); for (IProject project : ((IWorkspaceRoot) inputElement).getProjects()) { if (project.isOpen() && project.isAccessible()) { projects.add(project); } } return projects.toArray(); } return new Object[0]; } public void dispose() { } public void inputChanged(Viewer viewer, Object oldInput, Object newInput) { } } }