package jetbrains.mps.ide.java.platform.refactorings;
/*Generated by MPS */
import com.intellij.openapi.ui.DialogWrapper;
import jetbrains.mps.project.MPSProject;
import org.jetbrains.mps.util.Condition;
import org.jetbrains.mps.openapi.model.SNode;
import java.util.Set;
import org.jetbrains.mps.openapi.model.SModel;
import com.intellij.ui.treeStructure.SimpleTree;
import org.jetbrains.mps.openapi.model.SNodeReference;
import java.awt.HeadlessException;
import javax.swing.tree.DefaultMutableTreeNode;
import jetbrains.mps.ide.platform.modeltree.ModelTreeNode;
import jetbrains.mps.internal.collections.runtime.SetSequence;
import jetbrains.mps.internal.collections.runtime.IWhereFilter;
import jetbrains.mps.smodel.SModelStereotype;
import jetbrains.mps.internal.collections.runtime.ISelector;
import jetbrains.mps.ide.platform.modeltree.ModelTreeBuilder;
import org.jetbrains.annotations.Nullable;
import javax.swing.JComponent;
import javax.swing.tree.DefaultTreeModel;
import javax.swing.tree.TreeSelectionModel;
import jetbrains.mps.ide.platform.modeltree.ModelTreeCellRenderer;
import jetbrains.mps.internal.collections.runtime.Sequence;
import jetbrains.mps.internal.collections.runtime.ListSequence;
import jetbrains.mps.lang.smodel.generator.smodelAdapter.SModelOperations;
import jetbrains.mps.smodel.adapter.structure.MetaAdapterFactory;
import jetbrains.mps.lang.smodel.generator.smodelAdapter.SPropertyOperations;
import javax.swing.event.TreeSelectionListener;
import javax.swing.event.TreeSelectionEvent;
import jetbrains.mps.smodel.SNodePointer;
import javax.swing.JScrollPane;
import com.intellij.ui.ScrollPaneFactory;
import java.awt.Dimension;
import org.jetbrains.annotations.NonNls;
/*package*/ class ChooseNodeDialog extends DialogWrapper {
private final MPSProject myProject;
private final Condition<SNode> myApplicableNodes;
private final Set<SModel> myVisibleModels;
private SimpleTree myTree;
private SNodeReference mySelectedNode;
/**
* FIXME why not regular NodeChooserDialog, why dedicated class with custom tree?
* FIXME we use project here to access repository, although outer code uses repository from EditorContext
*/
public ChooseNodeDialog(MPSProject project, Condition<SNode> applicabilityCondition, Set<SModel> visibleModels, String title) throws HeadlessException {
super(project.getProject(), true);
setTitle(title);
myProject = project;
myApplicableNodes = applicabilityCondition;
myVisibleModels = visibleModels;
init();
}
protected boolean isAcceptable(SNode node) {
return myApplicableNodes.met(node);
}
private DefaultMutableTreeNode createRootNode() {
ModelTreeNode rootNode = new ModelTreeNode("Root");
for (SModel descriptor : SetSequence.fromSet(myVisibleModels).where(new IWhereFilter<SModel>() {
public boolean accept(SModel it) {
return !(SModelStereotype.isStubModel(it));
}
}).sort(new ISelector<SModel, String>() {
public String select(SModel it) {
return it.getReference().toString();
}
}, true)) {
rootNode.add(ModelTreeBuilder.createSModelTreeNode(descriptor));
}
return rootNode;
}
public SNodeReference getResult() {
return mySelectedNode;
}
@Nullable
@Override
protected JComponent createCenterPanel() {
final DefaultMutableTreeNode rootNode = createRootNode();
myTree = new SimpleTree(new DefaultTreeModel(rootNode));
myTree.getSelectionModel().setSelectionMode(TreeSelectionModel.SINGLE_TREE_SELECTION);
myTree.setCellRenderer(new ModelTreeCellRenderer());
myTree.setRootVisible(false);
myTree.setShowsRootHandles(true);
new ModelTreeBuilder(myTree) {
@Override
protected void initTreeNode(final ModelTreeNode node) {
if (node.getUserObject() instanceof SModel) {
myProject.getModelAccess().runReadInEDT(new Runnable() {
@Override
public void run() {
initModelDescriptorNode(node, (SModel) node.getUserObject());
}
});
}
}
private void initModelDescriptorNode(ModelTreeNode node, SModel descriptor) {
SModel sModel = descriptor;
for (SNode nextRoot : Sequence.fromIterable(ModelTreeBuilder.sortChildNodes(ListSequence.fromList(SModelOperations.roots(sModel, MetaAdapterFactory.getConcept(0xceab519525ea4f22L, 0x9b92103b95ca8c0cL, 0x10802efe25aL, "jetbrains.mps.lang.core.structure.BaseConcept"))).where(new IWhereFilter<SNode>() {
public boolean accept(SNode it) {
return isAcceptable(it);
}
})))) {
ModelTreeNode modelRootTreeNode = ModelTreeBuilder.createSNodeTreeNode(nextRoot);
modelRootTreeNode.setLeafPosition(true);
ModelTreeBuilder.insertChildSNodeTreeNode(node, modelRootTreeNode, SPropertyOperations.getString(nextRoot, MetaAdapterFactory.getProperty(0xceab519525ea4f22L, 0x9b92103b95ca8c0cL, 0x10802efe25aL, 0x115eca8579fL, "virtualPackage")));
}
notifyNodeStructureChanged(node);
}
};
myTree.getSelectionModel().addTreeSelectionListener(new TreeSelectionListener() {
@Override
public void valueChanged(TreeSelectionEvent event) {
Object selectedNode = event.getPath().getLastPathComponent();
if (selectedNode instanceof ModelTreeNode) {
ModelTreeNode treeNode = ((ModelTreeNode) selectedNode);
if (treeNode.getUserObject() instanceof SNodeReference) {
mySelectedNode = ((SNodePointer) treeNode.getUserObject());
getOKAction().setEnabled(true);
return;
}
}
getOKAction().setEnabled(false);
mySelectedNode = null;
}
});
JScrollPane scrollPane = ScrollPaneFactory.createScrollPane(myTree);
scrollPane.setPreferredSize(new Dimension(700, 500));
return scrollPane;
}
@Nullable
@NonNls
@Override
protected String getDimensionServiceKey() {
return getClass().getName();
}
}