| /******************************************************************************* |
| * Copyright (c) 2018 Agence spatiale canadienne / Canadian Space Agency |
| * 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: |
| * Pierre Allard, |
| * Regent L'Archeveque - initial API and implementation |
| * |
| * SPDX-License-Identifier: EPL-1.0 |
| *******************************************************************************/ |
| package org.eclipse.apogy.core.ui.wizards; |
| |
| import java.util.ArrayList; |
| import java.util.Collection; |
| import java.util.Iterator; |
| import java.util.List; |
| |
| import org.eclipse.apogy.common.emf.transaction.ApogyCommonTransactionFacade; |
| import org.eclipse.apogy.core.ApogyCorePackage; |
| import org.eclipse.apogy.core.ApogySystem; |
| import org.eclipse.apogy.core.AssemblyLink; |
| import org.eclipse.apogy.core.invocator.Type; |
| import org.eclipse.apogy.core.invocator.TypeMember; |
| import org.eclipse.emf.common.notify.AdapterFactory; |
| import org.eclipse.emf.edit.provider.ComposedAdapterFactory; |
| import org.eclipse.emf.edit.ui.provider.AdapterFactoryLabelProvider; |
| import org.eclipse.jface.viewers.ISelectionChangedListener; |
| import org.eclipse.jface.viewers.IStructuredSelection; |
| import org.eclipse.jface.viewers.ITreeContentProvider; |
| import org.eclipse.jface.viewers.SelectionChangedEvent; |
| import org.eclipse.jface.viewers.StructuredSelection; |
| import org.eclipse.jface.viewers.TreeViewer; |
| import org.eclipse.jface.viewers.Viewer; |
| import org.eclipse.swt.SWT; |
| import org.eclipse.swt.layout.FillLayout; |
| 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.Event; |
| import org.eclipse.swt.widgets.Group; |
| import org.eclipse.swt.widgets.Listener; |
| import org.eclipse.swt.widgets.Tree; |
| |
| public class AssemblyLinkDestinationWizardPage extends AbstractAssemblyLinkWizardPage { |
| private final static String WIZARD_PAGE_ID = "org.eclipse.apogy.core.ui.wizards.AssemblyLinkDestinationWizardPage"; |
| |
| private final AdapterFactory adapterFactory = new ComposedAdapterFactory( |
| ComposedAdapterFactory.Descriptor.Registry.INSTANCE); |
| |
| // Parent System |
| private Tree subSystemTree; |
| private TreeViewer subSystemTreeViewer; |
| private TypeMember selectedSubSystem = null; |
| |
| public AssemblyLinkDestinationWizardPage(ApogySystem apogySystem, AssemblyLink assemblyLink) { |
| super(WIZARD_PAGE_ID, apogySystem, assemblyLink); |
| |
| setTitle("Assembly link sub system"); |
| setDescription("Set the sub-system the assembly link refers to."); |
| |
| validate(); |
| } |
| |
| @Override |
| public void createControl(Composite parent) { |
| Composite container = new Composite(parent, SWT.None); |
| container.setLayout(new GridLayout(1, true)); |
| setControl(container); |
| |
| Group parentSystemGroup = new Group(container, SWT.BORDER); |
| parentSystemGroup.setLayout(new FillLayout()); |
| parentSystemGroup.setText("Sub-System"); |
| parentSystemGroup.setLayoutData(new GridData(SWT.FILL, SWT.FILL, true, true, 1, 1)); |
| |
| createParentSystemComposite(parentSystemGroup); |
| } |
| |
| private Composite createParentSystemComposite(Composite parent) { |
| Composite container = new Composite(parent, SWT.NONE); |
| container.setLayout(new GridLayout(2, false)); |
| |
| this.subSystemTreeViewer = new TreeViewer(container, |
| SWT.BORDER | SWT.H_SCROLL | SWT.V_SCROLL | SWT.FULL_SELECTION | SWT.MULTI); |
| this.subSystemTree = this.subSystemTreeViewer.getTree(); |
| GridData gd_tree = new GridData(SWT.FILL, SWT.FILL, false, true, 2, 1); |
| gd_tree.widthHint = 200; |
| gd_tree.minimumWidth = 200; |
| this.subSystemTree.setLayoutData(gd_tree); |
| this.subSystemTree.setLinesVisible(true); |
| |
| this.subSystemTreeViewer.setContentProvider(new ApogySystemContentProvider()); |
| this.subSystemTreeViewer.setLabelProvider(new AdapterFactoryLabelProvider(this.adapterFactory)); |
| this.subSystemTreeViewer.addSelectionChangedListener(new ISelectionChangedListener() { |
| |
| @Override |
| public void selectionChanged(SelectionChangedEvent event) { |
| AssemblyLinkDestinationWizardPage.this.selectedSubSystem = (TypeMember) ((IStructuredSelection) event |
| .getSelection()).getFirstElement(); |
| |
| // Updates sub-system. |
| ApogyCommonTransactionFacade.INSTANCE.basicSet(AssemblyLinkDestinationWizardPage.this.assemblyLink, |
| ApogyCorePackage.Literals.ASSEMBLY_LINK__SUB_SYSTEM_TYPE_MEMBER, |
| AssemblyLinkDestinationWizardPage.this.selectedSubSystem, true); |
| |
| validate(); |
| } |
| }); |
| this.subSystemTreeViewer.setInput(getAllTypeMembers(this.apogySystem)); |
| |
| Button btnClearParentSystem = new Button(container, SWT.NONE); |
| btnClearParentSystem.setSize(74, 29); |
| btnClearParentSystem.setText("Clear"); |
| btnClearParentSystem.setToolTipText( |
| "Clear the parent system for the Assembly Link. This is interprated as being the system itself."); |
| btnClearParentSystem.setLayoutData(new GridData(SWT.FILL, SWT.CENTER, true, false, 1, 1)); |
| btnClearParentSystem.setEnabled(true); |
| btnClearParentSystem.addListener(SWT.Selection, new Listener() { |
| @Override |
| public void handleEvent(Event event) { |
| // Clears the selection. This will trig the parentSystemTreeViewer response. |
| AssemblyLinkDestinationWizardPage.this.subSystemTreeViewer.setSelection(new StructuredSelection(), |
| true); |
| |
| validate(); |
| } |
| }); |
| |
| return container; |
| } |
| |
| @Override |
| protected List<TypeMember> getAllTypeMembers(ApogySystem apogySystem) { |
| List<TypeMember> list = new ArrayList<TypeMember>(); |
| |
| for (TypeMember member : apogySystem.getMembers()) { |
| list.addAll(recursiveGetAllTypeMembers(member)); |
| } |
| |
| return list; |
| } |
| |
| @Override |
| protected List<TypeMember> recursiveGetAllTypeMembers(TypeMember typeMember) { |
| List<TypeMember> list = new ArrayList<TypeMember>(); |
| list.add(typeMember); |
| |
| Type type = load(typeMember.getMemberType()); |
| |
| if (type != null) { |
| for (TypeMember member : type.getMembers()) { |
| list.addAll(recursiveGetAllTypeMembers(member)); |
| } |
| } |
| |
| return list; |
| } |
| |
| protected void validate() { |
| String errorMessage = null; |
| |
| if (this.assemblyLink.getSubSystemTypeMember() == null) { |
| errorMessage = "No Sub-System specified !"; |
| } |
| |
| setErrorMessage(errorMessage); |
| |
| setPageComplete(getErrorMessage() == null); |
| } |
| |
| private class ApogySystemContentProvider implements ITreeContentProvider { |
| List<AssemblyLink> allAssemblylinks; |
| |
| public ApogySystemContentProvider() { |
| this.allAssemblylinks = getAllAssemblyLinks(AssemblyLinkDestinationWizardPage.this.apogySystem); |
| } |
| |
| @Override |
| public void dispose() { |
| } |
| |
| @Override |
| public void inputChanged(Viewer viewer, Object oldInput, Object newInput) { |
| } |
| |
| @Override |
| public Object[] getElements(Object inputElement) { |
| if (inputElement instanceof Collection<?>) { |
| Collection<?> collection = (Collection<?>) inputElement; |
| return filter(collection).toArray(); |
| } |
| |
| return null; |
| } |
| |
| @Override |
| public Object[] getChildren(Object parentElement) { |
| if (parentElement instanceof Collection<?>) { |
| Collection<?> collection = (Collection<?>) parentElement; |
| return filter(collection).toArray(); |
| } |
| |
| return null; |
| } |
| |
| @Override |
| public Object getParent(Object element) { |
| return null; |
| } |
| |
| @Override |
| public boolean hasChildren(Object element) { |
| if (element instanceof Collection<?>) { |
| Collection<?> collection = (Collection<?>) element; |
| return filter(collection).isEmpty(); |
| } else { |
| return false; |
| } |
| } |
| |
| /** |
| * Filter out the type members that have already been assembled. |
| * |
| * @param members |
| * @return |
| */ |
| private Collection<TypeMember> filter(Collection<?> members) { |
| Collection<TypeMember> result = new ArrayList<TypeMember>(); |
| |
| for (Object obj : members) { |
| if (obj instanceof TypeMember) { |
| TypeMember typeMember = (TypeMember) obj; |
| |
| if (!isMapped(typeMember, this.allAssemblylinks)) { |
| result.add(typeMember); |
| } |
| } |
| } |
| |
| return result; |
| } |
| |
| private boolean isMapped(TypeMember typeMember, List<AssemblyLink> allAssemblylinks) { |
| boolean isMapped = false; |
| |
| Iterator<AssemblyLink> it = allAssemblylinks.iterator(); |
| // while(!isMapped && it.hasNext()) |
| while (it.hasNext()) { |
| AssemblyLink assemblyLink = it.next(); |
| |
| TypeMember target = assemblyLink.getSubSystemTypeMember(); |
| |
| if (target == typeMember) { |
| isMapped = true; |
| } |
| } |
| |
| return isMapped; |
| } |
| } |
| } |