package de.FeatureModellingTool.Pattern.UI;
import java.awt.Component;
import java.awt.event.ActionEvent;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Hashtable;
import java.util.Iterator;
import java.util.List;
import javax.swing.AbstractAction;
import javax.swing.Action;
import javax.swing.JOptionPane;
import javax.swing.JPopupMenu;
import research.ConnectionFigure;
import research.DrawingEditor;
import research.DrawingView;
import research.Figure;
import research.FigureEnumeration;
import research.SaturnDrawing;
import research.SaturnDrawingView;
import research.figure.ArrowTip;
import de.FeatureModellingTool.ElementInfoEditor.FeatureInfoEditor;
import de.FeatureModellingTool.FeatureModel.CompositeConstraintEditor;
import de.FeatureModellingTool.FeatureModel.ConstraintModelEditor;
import de.FeatureModellingTool.FeatureModel.Feature;
import de.FeatureModellingTool.FeatureModel.FeatureEditor;
import de.FeatureModellingTool.FeatureModel.FeatureModelEditor;
import de.FeatureModellingTool.FeatureModel.FeatureProperties;
import de.FeatureModellingTool.FeatureModel.FeatureRelation;
import de.FeatureModellingTool.FeatureModel.GroupConstraintEditor;
import de.FeatureModellingTool.FeatureModel.VPConstraintEditor;
import de.FeatureModellingTool.GraphicalEditor.ConstraintConnection;
import de.FeatureModellingTool.GraphicalEditor.CrossDecoration;
import de.FeatureModellingTool.GraphicalEditor.AttributeConnection;
import de.FeatureModellingTool.GraphicalEditor.GraphicalEditor;
import de.FeatureModellingTool.GraphicalEditor.DecomposeConnection;
import de.FeatureModellingTool.Pattern.ConstantDefinition;
import de.FeatureModellingTool.PatternBase.PatternBase;
import de.FeatureModellingTool.PatternBase.Templete;
import de.reuse.DrawingEditorTabbedPane;
public class PatternGraphicalEditor extends
de.FeatureModellingTool.GraphicalEditor.GraphicalEditorImplementation {
PatternBase patternBase = null;
Templete template = null;
FeatureEditor featureEditor = null;
FeatureModelEditor featureModelEditor = null;
ConstraintModelEditor constraintModelEditor = null;
GroupConstraintEditor groupConstraintEditor = null;
CompositeConstraintEditor compositeConstraintEditor = null;
VPConstraintEditor vpConstraintEditor = null;
private Component container = null;
private AbstractAction featureInfoEditorEntryAction = null;
public PatternGraphicalEditor(Component container , PatternBase patternBase)
{
super();
this.container = container;
this.patternBase = patternBase;
DrawingView view = new SaturnDrawingView(1600, 5000);
view.setDrawing(new SaturnDrawing());
this.editorArea.add(view);
}
public void setTemplate(Templete template) {
this.template = template;
JPopupMenu popupMenu = getGraphicalEditorUI().getEditorAreaPopupMenu();
popupMenu.removeAll();
if (this.template==null) {
this.featureEditor = null;
this.featureModelEditor = null;
this.constraintModelEditor = null;
this.groupConstraintEditor = null;
this.compositeConstraintEditor = null;
this.vpConstraintEditor = null;
this.getContext().putValue(GraphicalEditor.FEATURE_MODEL, null);
this.getContext().putValue(GraphicalEditor.FEATURE_EDITOR, null);
this.getContext().putValue(GraphicalEditor.FEATURE_MODEL_EDITOR, null);
this.getContext().putValue(GraphicalEditor.FEATURE_RELATION_MANAGER, null);
this.getContext().putValue(GraphicalEditor.CONSTRAINT_MODEL, null);
this.getContext().putValue(GraphicalEditor.CONSTRAINT_MODEL_EDITOR, null);
this.getContext().putValue(GraphicalEditor.PL_CONSTRAINT_EDITOR, null);
this.getContext().putValue(GraphicalEditor.GROUP_CONSTRAINT_EDITOR, null);
this.getContext().putValue(GraphicalEditor.VP_CONSTRAINT_EDITOR, null);
this.getContext().putValue(GraphicalEditor.INTERACTION_MODEL, null);
this.getContext().putValue(GraphicalEditor.RESOURCE_COMPONENT_EDITOR, null);
this.getContext().putValue(GraphicalEditor.INTERACTION_MODEL_EDITOR, null);
} else {
this.featureEditor = this.template.getFeatureEditor();
this.featureModelEditor = this.template.getFeatureModelEditor();
this.constraintModelEditor = this.template.getConstraintModelEditor();
this.groupConstraintEditor = (GroupConstraintEditor)this.template.getFComponent().getInterface(de.FeatureModellingTool.FeatureModel.Manager.GROUP_CONSTRAINT_EDITOR_INTERFACE);
this.compositeConstraintEditor = (CompositeConstraintEditor)this.template.getFComponent().getInterface(de.FeatureModellingTool.FeatureModel.Manager.PL_CONSTRAINT_EDITOR_INTERFACE);
this.vpConstraintEditor = this.template.getVpConstraintEditor();
this.getContext().putValue(GraphicalEditor.FEATURE_MODEL, this.template.getFComponent().getInterface(de.FeatureModellingTool.FeatureModel.Manager.FEATURE_MODEL_INTERFACE));
this.getContext().putValue(GraphicalEditor.FEATURE_EDITOR, this.featureEditor);
this.getContext().putValue(GraphicalEditor.FEATURE_MODEL_EDITOR, this.featureModelEditor);
this.getContext().putValue(GraphicalEditor.FEATURE_RELATION_MANAGER, this.template.getFComponent().getInterface(de.FeatureModellingTool.FeatureModel.Manager.FEATURE_RELATION_MANAGER_INTERFACE));
this.getContext().putValue(GraphicalEditor.CONSTRAINT_MODEL, this.template.getFComponent().getInterface(de.FeatureModellingTool.FeatureModel.Manager.CONSTRAINT_MODEL_INTERFACE));
this.getContext().putValue(GraphicalEditor.CONSTRAINT_MODEL_EDITOR, constraintModelEditor);
this.getContext().putValue(GraphicalEditor.PL_CONSTRAINT_EDITOR, this.compositeConstraintEditor);
this.getContext().putValue(GraphicalEditor.GROUP_CONSTRAINT_EDITOR, this.groupConstraintEditor);
this.getContext().putValue(GraphicalEditor.VP_CONSTRAINT_EDITOR, this.vpConstraintEditor);
this.getContext().putValue(GraphicalEditor.INTERACTION_MODEL, this.template.getFComponent().getInterface(de.FeatureModellingTool.FeatureModel.Manager.INTERACTION_MODEL_INTERFACE));
this.getContext().putValue(GraphicalEditor.RESOURCE_COMPONENT_EDITOR, this.template.getFComponent().getInterface(de.FeatureModellingTool.FeatureModel.Manager.RESOURCE_COMPONENT_EDITOR_INTERFACE));
this.getContext().putValue(GraphicalEditor.INTERACTION_MODEL_EDITOR, this.template.getFComponent().getInterface(de.FeatureModellingTool.FeatureModel.Manager.INTERACTION_MODEL_EDITOR_INTERFACE));
FeatureInfoEditor featureInfoEditor = de.FeatureModellingTool.ElementInfoEditor.Manager.createFeatureInfoEditor();
featureInfoEditor = de.FeatureModellingTool.ElementInfoEditor.Manager.createFeatureInfoEditor();
featureInfoEditor.getContext().putValue(de.FeatureModellingTool.ElementInfoEditor.ConstantDefinition.FEATURE_MODEL, featureModel);
featureInfoEditor.getContext().putValue(de.FeatureModellingTool.ElementInfoEditor.ConstantDefinition.FEATURE_EDITOR, featureEditor);
featureInfoEditor.getContext().putValue(de.FeatureModellingTool.ElementInfoEditor.ConstantDefinition.FEATURE_MODEL_EDITOR, featureModelEditor);
// featureInfoEditor.getContext().putValue(de.FeatureModellingTool.ElementInfoEditor.ConstantDefinition.GRAPHICAL_EDITOR, pge);
featureInfoEditor.getContext().putValue(de.FeatureModellingTool.ElementInfoEditor.ConstantDefinition.FEATURE_RELATION_MANAGER, this.template.getFComponent().getInterface(de.FeatureModellingTool.FeatureModel.Manager.FEATURE_RELATION_MANAGER_INTERFACE));
featureInfoEditor.getContext().putValue(de.FeatureModellingTool.ElementInfoEditor.ConstantDefinition.CONTAINER, this.container);
Action deleteAction = (Action) getActionMap().get(de.FeatureModellingTool.GraphicalEditor.ConstantDefinition.FIGURE_DELETE_ACTION);
deleteAction.putValue(de.FeatureModellingTool.GraphicalEditor.ConstantDefinition.FEATURE_MODEL, featureModel);
deleteAction.putValue(de.FeatureModellingTool.GraphicalEditor.ConstantDefinition.FEATURE_MODEL_EDITOR, featureModelEditor);
deleteAction.putValue(de.FeatureModellingTool.GraphicalEditor.ConstantDefinition.CONSTRAINT_MODEL, constraintModel);
deleteAction.putValue(de.FeatureModellingTool.GraphicalEditor.ConstantDefinition.CONSTRAINT_MODEL_EDITOR, constraintModelEditor);
deleteAction.putValue(de.FeatureModellingTool.GraphicalEditor.ConstantDefinition.INTERACTION_MODEL, interactionModel);
deleteAction.putValue(de.FeatureModellingTool.GraphicalEditor.ConstantDefinition.INTERACTION_MODEL_EDITOR, this.template.getFComponent().getInterface(de.FeatureModellingTool.FeatureModel.Manager.INTERACTION_MODEL_EDITOR_INTERFACE));
featureInfoEditor.getContext().putValue(de.FeatureModellingTool.ElementInfoEditor.ConstantDefinition.GRAPHICAL_EDITOR , this);
this.featureInfoEditorEntryAction = (AbstractAction)featureInfoEditor.getEntryAction();
this.editorArea.firePropertyChange(DrawingEditor.CURRENT_VIEW_CHANGED , 1, 1);
popupMenu.add(featureInfoEditor.getEntryAction());
popupMenu.add(deleteAction);
popupMenu.add(getEditParameterAction());
popupMenu.add(getCloneFeatureTreeAction());
popupMenu.add(getUsePatternAction());
}
this.refreshUI();
}
public DrawingEditorTabbedPane getEditorArea()
{
return super.editorArea;
}
protected void refreshFigures() {
DrawingView dv = this.getEditorArea().view();
// remove all figures
Collection<Figure> figures = new ArrayList<Figure>();
FigureEnumeration fe = dv.getDrawing().getFigures();
while (fe.hasMoreElements())
figures.add(fe.nextFigure());
for (Iterator<Figure> itFigure = figures.iterator() ; itFigure.hasNext() ; )
dv.remove(itFigure.next());
super.idToFigureMap.clear();
if (this.featureModel==null || featureModel.getAllFeature().values().size()==0) {
return;
}
// add new figures
Hashtable<String , Figure> htFigures = new Hashtable<String , Figure>();
AutoLayout_Feature featureLayout = new AutoLayout_Feature();
for (Iterator itFeature = this.featureModel.getAllFeature().values().iterator() ; itFeature.hasNext() ; )
{
Feature feature = (Feature)itFeature.next();
PatternFeatureFigure figure = new PatternFeatureFigure();
figure.setText(feature.getName());
figure.setAttribute("id" , feature.getID());
figure.setAttribute(FeatureProperties.VARIABILITY , feature.getVariability().getName());
figure.setAttribute(de.FeatureModellingTool.Pattern.ConstantDefinition.FEATURE_ATTRIBUTE_COUNT , Integer.toString(this.template.getParameters().getFeatureNum(feature.getID())));
dv.add(figure);
htFigures.put(feature.getID() , figure);
super.idToFigureMap.add(feature.getID() , figure);
featureLayout.addFeature(feature , figure.size().width , figure.size().height);
}
featureLayout.caculateLayout();
for (Iterator itFeature = this.featureModel.getAllFeature().values().iterator() ; itFeature.hasNext() ; )
{
Feature feature = (Feature)itFeature.next();
AutoLayout_Feature.FeatureLayout fl = featureLayout.getFeatureLayout(feature);
Figure figure = htFigures.get(feature.getID());
figure.moveBy(30 + fl.x, 30 + fl.y);
// figure.setDisplayBox(new Rectangle(fl.x , fl.y));
}
if (this.featureModel.getAllFeatureRelation()!=null)
for (Iterator itRelation = this.featureModel.getAllFeatureRelation().values().iterator() ; itRelation.hasNext() ; )
{
FeatureRelation featureRelation = (FeatureRelation)itRelation.next();
ConnectionFigure cf = null;
if (FeatureRelation.ATTRIBUTE.equals(featureRelation.getName())) {
AttributeConnection dvc = new AttributeConnection();
cf = dvc;
} else if (FeatureRelation.DECOMPOSE.equals(featureRelation.getName())) {
DecomposeConnection ic = new DecomposeConnection();
cf = ic;
} else if (FeatureRelation.REQUIRE.equals(featureRelation.getName())) {
ConstraintConnection cc = new ConstraintConnection(FeatureRelation.REQUIRE);
cc.setEndDecoration(new ArrowTip());
cf = cc;
} else if (FeatureRelation.EXCLUDE.equals(featureRelation.getName())) {
ConstraintConnection cc = new ConstraintConnection(FeatureRelation.EXCLUDE);
cc.setMidDecoration(new CrossDecoration(5));
cf = cc;
}
if (cf!=null) {
cf.setAttribute("id" , featureRelation.getID());
cf.startPoint(htFigures.get(featureRelation.getStartFeature().getID()).center().x , htFigures.get(featureRelation.getStartFeature().getID()).center().y);
cf.endPoint(htFigures.get(featureRelation.getEndFeature().getID()).center().x , htFigures.get(featureRelation.getEndFeature().getID()).center().y);
if (de.FeatureModellingTool.Pattern.ConstantDefinition.isStructRelation(featureRelation)) {
cf.connectStart(htFigures.get(featureRelation.getStartFeature().getID()).getConnectors()[2]);
cf.connectEnd(htFigures.get(featureRelation.getEndFeature().getID()).getConnectors()[1]);
} else {
cf.connectStart(htFigures.get(featureRelation.getStartFeature().getID()).getConnectors()[0]);
cf.connectEnd(htFigures.get(featureRelation.getEndFeature().getID()).getConnectors()[0]);
}
dv.add(cf);
cf.updateConnection();
htFigures.put(featureRelation.getID() , cf);
super.idToFigureMap.add(featureRelation.getID() , cf);
}
}
}
public void refreshUI()
{
this.editorArea.getCurrentView().clearSelection();
this.refreshFigures();
this.getEditorArea().updateUI();
}
protected CloneFeatureTreeAction cloneFeatureTreeAction = new CloneFeatureTreeAction();
public CloneFeatureTreeAction getCloneFeatureTreeAction() {
return this.cloneFeatureTreeAction;
}
protected UsePatternAction usePatternAction = new UsePatternAction();
public UsePatternAction getUsePatternAction() {
return this.usePatternAction;
}
protected EditParameterAction editParameterAction = new EditParameterAction();
public EditParameterAction getEditParameterAction() {
return this.editParameterAction;
}
protected void updateEditActionsUI() {
super.updateEditActionsUI();
this.cloneFeatureTreeAction.firePropertyChange("enabled" , !this.cloneFeatureTreeAction.isEnabled() , this.cloneFeatureTreeAction.isEnabled());
this.usePatternAction.firePropertyChange("enabled" , !this.usePatternAction.isEnabled() , this.usePatternAction.isEnabled());
this.editParameterAction.firePropertyChange("enabled" , !this.editParameterAction.isEnabled() , this.editParameterAction.isEnabled());
if (this.featureInfoEditorEntryAction!=null)
this.featureInfoEditorEntryAction.setEnabled(this.featureInfoEditorEntryAction.isEnabled());
}
protected class CloneFeatureTreeAction extends EditorAction {
protected boolean isDoing = false;
protected int count = 0;
public CloneFeatureTreeAction() {
this.putValue(Action.NAME, "Clone Feature");
isDoing = false;
}
public boolean isEnabled() {
if (!super.isEnabled()) return false;
if (editorArea.getCurrentView() == null) return false;
boolean result = false;
List selection = getSelection();
if (selection != null) {
for (int i = 0; i < selection.size(); i++) {
String fID = (String) selection.get(i);
result = result || featureModel.containsFeature(fID);
if (featureModel.getRootFeature(fID)==null || fID.equals(featureModel.getRootFeature(fID).getID())) {
return false;
}
}
}
return result;
}
public void actionPerformed(ActionEvent e) {
if (!isEnabled()) return;
if (isDoing) return;
isDoing = true;
List selection = getSelection();
if (selection != null) {
for (int i = 0; i < selection.size(); i++) {
String fID = (String) selection.get(i);
Feature feature = featureModel.getFeature(fID);
if (feature!=null) {
de.FeatureModellingTool.Pattern.FeatureModelHelper.cloneFeatureTree(feature , featureEditor , featureModel , featureModelEditor , constraintModel , constraintModelEditor , groupConstraintEditor , compositeConstraintEditor , vpConstraintEditor);
}
}
}
refreshUI();
isDoing = false;
}
}
protected class UsePatternAction extends EditorAction {
public UsePatternAction() {
this.putValue(Action.NAME, "Use Pattern");
}
public boolean isEnabled() {
if (!super.isEnabled()) return false;
if (editorArea.getCurrentView() == null) return false;
return template!=null;
}
public void actionPerformed(ActionEvent e) {
if (!isEnabled()) return;
List selection = getSelection();
if (selection != null) {
PatternSelection patternSelection = new PatternSelection(patternBase);
int result = JOptionPane.showConfirmDialog(container, patternSelection, "��ѡ����Ҫ���õ�ģʽ"
,JOptionPane.OK_CANCEL_OPTION, JOptionPane.INFORMATION_MESSAGE);
if (result == JOptionPane.OK_OPTION && patternSelection.template!=null) {
Hashtable<String , Integer> htCount = patternSelection.getCloneCount();
Feature root = (Feature)patternSelection.template.getFeatureModel().getAllFeature().values().iterator().next();
root = patternSelection.template.getFeatureModel().getRootFeature(root.getID());
for (int i = 0; i < selection.size(); i++) {
String fID = (String) selection.get(i);
Feature feature = featureModel.getFeature(fID);
if (feature!=null) {
Hashtable<String , String>nameMap = new Hashtable<String , String>();
Hashtable<String , Figure>figureMap = new Hashtable<String , Figure>();
de.FeatureModellingTool.Pattern.FeatureModelHelper.pasteFeatureTree(root, patternSelection.template.getFeatureModel(), patternSelection.template.getConstraintModel(), feature , featureModel, constraintModel, editorArea.getCurrentView(), featureModelEditor , featureEditor , htCount , nameMap , figureMap);
}
}
refreshUI();
}
}
}
}
protected class EditParameterAction extends EditorAction {
public EditParameterAction() {
this.putValue(Action.NAME, "Edit Parameter");
}
public boolean isEnabled() {
if (!super.isEnabled()) return false;
if (editorArea.getCurrentView() == null) return false;
List selection = getSelection();
return template!=null && selection!=null && selection.size()==1;
}
public void actionPerformed(ActionEvent e) {
if (!isEnabled()) return;
List selection = getSelection();
if (selection != null && selection.size()==1) {
ParameterEditor editor = new ParameterEditor();
editor.setParameter(Integer.toString(template.getParameters().getFeatureNum((String)selection.get(0))));
int result = JOptionPane.showConfirmDialog(container, editor, "������������"
,JOptionPane.OK_CANCEL_OPTION, JOptionPane.INFORMATION_MESSAGE);
if (result == JOptionPane.OK_OPTION) {
int num = 1;
try {
num = Integer.parseInt(editor.getParameter());
} catch (Exception ex)
{
if ("n".equals(editor.getParameter())) {
num = 0;
}
}
template.getParameters().setFeatureNum((String)selection.get(0) , num);
refreshUI();
}
}
}
}
public CurrentTemplateChangeListener getCurrentTemplateChangeListener() {
return new CurrentTemplateChangeListener();
}
protected class CurrentTemplateChangeListener implements PropertyChangeListener {
public void propertyChange(PropertyChangeEvent evt) {
if (evt.getPropertyName().equals(ConstantDefinition.CURRENT_TEMPLATE)) {
Templete template = (Templete)evt.getNewValue();
setTemplate(template);
}
}
}
}