package org.eclipse.uml2.diagram.sequence.internal.layout.model;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Set;
import org.eclipse.emf.ecore.EObject;
import org.eclipse.gmf.runtime.notation.View;
import org.eclipse.uml2.diagram.sequence.internal.layout.abstractgde.AbsNode;
import org.eclipse.uml2.diagram.sequence.internal.layout.abstractgde.AbsNodeEnumeration;
import org.eclipse.uml2.diagram.sequence.internal.layout.vertical.input.LifeLineElement;
import org.eclipse.uml2.diagram.sequence.internal.missed.MissedMethods;
/**
*
*/
public abstract class LMBracketContainer implements LmReshapable, SelfReorderable {
LMBracketContainer(AbsNode gdeNode, LmOwner lmOwner) {
myGdeNode = gdeNode;
myLmOwner = lmOwner;
}
public abstract LmBracketsList getChildBracketsList();
public AbsNode getGdeNode() {
return myGdeNode;
}
abstract LMLifeLine getLifeLine();
abstract LMFrame getContainingFrame();
abstract LMGenCallOccurence getContainingCallOccurence();
abstract LMLifeLineBracket getCreationCandidate();
abstract LMLifeLineBracket getDestructionCandidate();
protected class ChildBracketsNFIterator implements SDVerticalLayoutInputImpl.NullFreeIterator {
private final Iterator myIterator = getChildBracketsList().iterator();
/*{
assertChildBracketsInCorrectOrder();
for (Iterator it = getChildBracketsList().iterator(); it.hasNext(); ) {
LMLifeLineBracket bracket1 = (LMLifeLineBracket) it.next();
if (bracket1.getContainer() != LMBracketContainer.this) {
throw new RuntimeException("Bad container of "+bracket1+" : "+bracket1.getContainer());
}
}
}
*/ public Object next() {
if (!myIterator.hasNext()) {
return null;
}
LMLifeLineBracket bracket1 = (LMLifeLineBracket) myIterator.next();
return bracket1.verticalLayoutElements();
}
}
abstract LMLifeLineBracket createChildBracketInstance(AbsNode gdeNode, View reference);
protected abstract Integer getClueValue();
void assertChildBracketsInCorrectOrder() {
if (myLmOwner.reorderAgainstModelNotGde()) {
assertLmOrderAgainstModel();
} else {
assertGdeOrderAgainstModel();
assertLmOrderAgainstGde();
}
}
private void assertGdeOrderAgainstModel() {
EObject entity = getGdeNode().getModelEntity();
if (entity == null) {
return;
}
List modelChildren = MissedMethods._arcasMetamodelSpecific().getArcasMetamodelChildren(getGdeNode().getReference());
Set modelChildrenSet = new HashSet(modelChildren);
List gdeOrderOfModelChildren = new ArrayList();
for (AbsNodeEnumeration gdeNodeEnum = getGdeNode().subnodes(); gdeNodeEnum.hasMoreElements(); ) {
AbsNode node1 = gdeNodeEnum.nextGdeNode();
EObject nodeEntity1 = node1.getModelEntity();
if (modelChildrenSet.contains(nodeEntity1)) {
gdeOrderOfModelChildren.add(nodeEntity1);
}
}
try {
SdLayoutUtil.assertCorrectSubList(modelChildren, gdeOrderOfModelChildren);
} catch (RuntimeException e) {
throw new RuntimeException("Problem asserting order gde-model (updater-gde problem, probably)", e); //$NON-NLS-1$
}
}
private void assertLmOrderAgainstModel() {
EObject entity = getGdeNode().getModelEntity();
if (entity == null) {
return;
}
List entities = new ArrayList();
for (Iterator it=getChildBracketsList().iterator(); it.hasNext(); ) {
LMLifeLineBracket bracket1 = (LMLifeLineBracket) it.next();
AbsNode node1 = bracket1.getGdeNode();
EObject nodeEntity1 = node1.getModelEntity();
if (nodeEntity1 == null) {
//throw new RuntimeException("Cannot get model entity from "+bracket1);
continue;
}
entities.add(nodeEntity1);
}
List realEntitiesList = MissedMethods._arcasMetamodelSpecific().getArcasMetamodelChildren(getGdeNode().getReference());
//System.out.println("[LMBracketContainer.assertChildBracketsInCorrectOrder] realEntitiesList="+realEntitiesList);
//System.out.println("[LMBracketContainer.assertChildBracketsInCorrectOrder] entities="+entities);
try {
SdLayoutUtil.assertCorrectSubList(realEntitiesList, entities);
} catch (RuntimeException e) {
throw new RuntimeException("Problem asserting order against model (lm reorder problem, probably)", e); //$NON-NLS-1$
}
}
private void assertLmOrderAgainstGde() {
List gdeNodes = new ArrayList();
for (Iterator it=getChildBracketsList().iterator(); it.hasNext(); ) {
LMLifeLineBracket bracket1 = (LMLifeLineBracket) it.next();
AbsNode node1 = bracket1.getGdeNode();
gdeNodes.add(node1);
}
try {
SdLayoutUtil.assertCorrectSubList(Collections.list(getGdeNode().subnodes()), gdeNodes);
} catch (RuntimeException e) {
throw new RuntimeException("Problem asserting order against gde (our problem, probably)", e); //$NON-NLS-1$
}
}
public void reorderChildElements() {
if (myLmOwner.reorderAgainstModelNotGde()) {
LinkedHashMap entity2bracketIndex = new LinkedHashMap();
List oldGdeOrder = new ArrayList();
int index = 0;
for (Iterator it=getChildBracketsList().iterator(); it.hasNext(); ) {
LMLifeLineBracket bracket1 = (LMLifeLineBracket) it.next();
AbsNode node1 = bracket1.getGdeNode();
oldGdeOrder.add(node1);
EObject nodeEntity1 = node1.getModelEntity();
Integer anotherBracketIndex = (Integer) entity2bracketIndex.put(nodeEntity1, new Integer(index));
if (anotherBracketIndex != null) {
throw new RuntimeException("In container 2 brackets are associated with one entity"); //$NON-NLS-1$
}
index ++;
}
List oldIndexList = new ArrayList(getChildBracketsList().size());
View reference = getGdeNode().getReference();
for (EObject nextEntity : MissedMethods._arcasMetamodelSpecific().getArcasMetamodelChildren(reference)) {
Integer oldIndex = (Integer) entity2bracketIndex.remove(nextEntity);
if (oldIndex != null) {
oldIndexList.add(oldIndex);
}
}
oldIndexList.addAll(entity2bracketIndex.values());
// List oldOrder = new ArrayList(getChildBracketsList().getListView());
getChildBracketsList().reorderList(oldIndexList);
// List newOrder = new ArrayList(getChildBracketsList().getListView());
//assertChildBracketsInCorrectOrder();
} else {
LinkedHashMap gdeNode2bracketIndex = new LinkedHashMap();
int index = 0;
for (Iterator it=getChildBracketsList().iterator(); it.hasNext(); ) {
LMLifeLineBracket bracket1 = (LMLifeLineBracket) it.next();
AbsNode node1 = bracket1.getGdeNode();
Integer anotherBracketIndex = (Integer) gdeNode2bracketIndex.put(node1, new Integer(index));
if (anotherBracketIndex != null) {
throw new RuntimeException("In container 2 brackets are associated with one gde node"); //$NON-NLS-1$
}
index ++;
}
List oldIndexList = new ArrayList(getChildBracketsList().size());
for (AbsNodeEnumeration gdeNodeEnum = getGdeNode().subnodes(); gdeNodeEnum.hasMoreElements(); ) {
AbsNode gdeNode1 = gdeNodeEnum.nextGdeNode();
Integer oldIndex = (Integer) gdeNode2bracketIndex.remove(gdeNode1);
if (oldIndex != null) {
oldIndexList.add(oldIndex);
}
}
oldIndexList.addAll(gdeNode2bracketIndex.values());
//List oldOrder = new ArrayList(getChildBracketsList().getListView());
getChildBracketsList().reorderList(oldIndexList);
//List newOrder = new ArrayList(getChildBracketsList().getListView());
//try {
//assertChildBracketsInCorrectOrder();
//} catch (RuntimeException e) {
// throw new RuntimeException("Problem with reordering,\noldOrder="+oldOrder+",\nnewOrder="+newOrder+",\nreordering indices="+oldIndexList, e);
//}
}
}
public void reorderAfterReading() {
if (myLmOwner.reorderAgainstModelNotGde()) {
reorderChildElements();
}
}
public void setJustReshaped(JustReshapedState justReshapedState) {
myJustReshapedState = justReshapedState;
}
protected boolean isJustReshaped() {
if (myJustReshapedState == null) {
return false;
}
return myJustReshapedState.isStillJustReshaped();
}
private JustReshapedState myJustReshapedState = null;
protected void setBracketTopPos(int pos) {
getGdeNode().setY(pos);
}
protected void setBracketBottomPos(int pos) {
getGdeNode().setHeight(pos - getGdeNode().getY());
}
protected int getBracketTopPos() {
return getGdeNode().getY();
}
protected int getBracketBottomPos() {
return getGdeNode().getY() + getGdeNode().getHeight();
}
protected LmOwner getLmOwner() {
return myLmOwner;
}
private final AbsNode myGdeNode;
private final LmOwner myLmOwner;
protected class BracketTopPosition implements LifeLineElement.Position {
public int getPositionValue() {
return getBracketTopPos();
}
public void setPositionValue(int pos) {
setBracketTopPos(pos);
}
public boolean isVirtual() {
return false;
}
public boolean isFirstPrioritedPosition() {
return isJustReshaped();
}
public boolean isLastPrioritedPosition() {
return false;
}
}
protected class BracketBottomPosition implements LifeLineElement.Position {
public int getPositionValue() {
return getBracketBottomPos();
}
public void setPositionValue(int pos) {
setBracketBottomPos(pos);
}
public boolean isVirtual() {
return false;
}
public boolean isFirstPrioritedPosition() {
return false;
}
public boolean isLastPrioritedPosition() {
return isJustReshaped();
}
}
}