blob: 7bca8f9e471b49b2dbaa3c9bd89cd8536acdd8d3 [file] [log] [blame]
/*******************************************************************************
* 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;
}
}
}