blob: 8f45c9d10607929de11eeae98fcbb1830c3cc5b4 [file] [log] [blame]
/*******************************************************************************
* Copyright (c) 2007 committers of openArchitectureWare and others.
* 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:
* committers of openArchitectureWare - initial API and implementation
*******************************************************************************/
package org.eclipse.xpand.ui.debug;
import static org.eclipse.internal.xpand2.debug.XpandElementAdapter.TYPE;
import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import org.eclipse.core.resources.IResource;
import org.eclipse.core.runtime.FileLocator;
import org.eclipse.core.runtime.IPath;
import org.eclipse.core.runtime.Path;
import org.eclipse.emf.mwe.ui.workflow.util.PluginConfigurationElementUtil;
import org.eclipse.internal.xpand2.ast.AbstractDefinition;
import org.eclipse.internal.xpand2.ast.ErrorStatement;
import org.eclipse.internal.xpand2.ast.ExpandStatement;
import org.eclipse.internal.xpand2.ast.ExpressionStatement;
import org.eclipse.internal.xpand2.ast.FileStatement;
import org.eclipse.internal.xpand2.ast.ForEachStatement;
import org.eclipse.internal.xpand2.ast.IfStatement;
import org.eclipse.internal.xpand2.ast.LetStatement;
import org.eclipse.internal.xpand2.ast.ProtectStatement;
import org.eclipse.internal.xpand2.ast.Statement;
import org.eclipse.internal.xpand2.ast.Template;
import org.eclipse.internal.xpand2.ast.TextStatement;
import org.eclipse.internal.xpand2.debug.ExpandSpecial;
import org.eclipse.internal.xpand2.debug.ForEachSpecial;
import org.eclipse.internal.xpand2.debug.IfSpecial;
import org.eclipse.internal.xpand2.debug.XpandModelPresentation;
import org.eclipse.internal.xpand2.model.XpandAdvice;
import org.eclipse.internal.xpand2.model.XpandDefinition;
import org.eclipse.internal.xtend.expression.ast.Expression;
import org.eclipse.internal.xtend.expression.ast.ISyntaxElement;
import org.eclipse.internal.xtend.expression.ast.SyntaxElement;
import org.eclipse.internal.xtend.expression.debug.EvaluatedElementWrapper;
import org.eclipse.internal.xtend.expression.debug.NoResourceSpecial;
import org.eclipse.swt.graphics.Image;
import org.eclipse.swt.graphics.ImageData;
import org.eclipse.swt.widgets.Display;
import org.eclipse.xpand.ui.XpandEditorPlugin;
import org.eclipse.xpand.ui.editor.XpandEditor;
import org.eclipse.xpand.ui.internal.XpandLog;
import org.eclipse.xtend.shared.ui.core.IXtendXpandResource;
import org.eclipse.xtend.ui.debug.ExpressionPluginAdapter;
/**
* The IPluginAdapter implementation for Xpand statements.
*
* @author Clemens Kadura (zAJKa)
* @author Karsten Thoms (itemis) - maintenance
* @author Aykut Kilic (itemis) - Bug#465802, 484406, 480679
*/
public class XpandPluginAdapter extends ExpressionPluginAdapter {
public XpandPluginAdapter() {
super();
specials.add(new ForEachSpecial());
specials.add(new ExpandSpecial());
specials.add(new IfSpecial());
specials.add(new NoResourceSpecial());
pres = new XpandModelPresentation(specials);
}
// -------------------------------------------------------------------------
@Override
protected String getRequiredExtension() {
return "xpt";
}
@Override
public boolean canHandleType(final String type) {
return TYPE.equals(type);
}
@Override
public String getEditorId() {
return PluginConfigurationElementUtil
.getConfigAttribute("org.eclipse.ui.editors/" + "editor[class="
+ XpandEditor.class.getName() + "]/id");
}
// -------------------------------------------------------------------------
@Override
protected List<ISyntaxElement> collectFirstLevelElements(
final IXtendXpandResource res) {
if (res == null)
return Collections.emptyList();
List<ISyntaxElement> result = new ArrayList<ISyntaxElement>();
XpandDefinition[] defs = ((Template) res.getExtXptResource())
.getDefinitions();
for (XpandDefinition def : defs)
result.add(def);
XpandAdvice[] advs = ((Template) res.getExtXptResource()).getAdvices();
for (XpandAdvice adv : advs)
result.add(adv);
return result;
}
@Override
protected List<ISyntaxElement> getBody(final ISyntaxElement parent) {
List<ISyntaxElement> result = new ArrayList<ISyntaxElement>();
// Definition or Advice
if (parent instanceof AbstractDefinition) {
result.addAll(((AbstractDefinition) parent).getBodyAsList());
}
// TextStatement
else if (parent instanceof TextStatement) {
// don't handle text
}
// FileStatement
else if (parent instanceof FileStatement) {
FileStatement stmt = (FileStatement) parent;
result.add(new EvaluatedElementWrapper(parent));
result.add(stmt.getTargetFileName());
result.addAll(stmt.getBodyAsList());
}
// ForEachStatement
else if (parent instanceof ForEachStatement) {
ForEachStatement stmt = (ForEachStatement) parent;
result.add(new EvaluatedElementWrapper(parent));
result.add(stmt.getTarget());
result.add(stmt.getSeparator());
result.addAll(stmt.getBodyAsList());
}
// IfStatement
else if (parent instanceof IfStatement) {
IfStatement stmt = (IfStatement) parent;
result.add(new EvaluatedElementWrapper(parent));
result.add(stmt.getCondition());
result.addAll(stmt.getBodyAsList());
result.add(stmt.getElseIf());
}
// LetStatement
else if (parent instanceof LetStatement) {
LetStatement stmt = (LetStatement) parent;
result.add(new EvaluatedElementWrapper(parent));
result.add(stmt.getVarValue());
result.addAll(stmt.getBodyAsList());
}
// ProtectStatement
else if (parent instanceof ProtectStatement) {
ProtectStatement stmt = (ProtectStatement) parent;
result.add(new EvaluatedElementWrapper(parent));
result.add(stmt.getCommentStart());
result.add(stmt.getCommentEnd());
result.add(stmt.getId());
result.addAll(stmt.getBodyAsList());
}
// ErrorStatement
else if (parent instanceof ErrorStatement) {
result.add(new EvaluatedElementWrapper(parent));
result.add(((ErrorStatement) parent).getMessage());
}
// ExpandStatement
else if (parent instanceof ExpandStatement) {
ExpandStatement stmt = (ExpandStatement) parent;
result.add(new EvaluatedElementWrapper(parent));
result.addAll(stmt.getParametersAsList());
Expression target = ((ExpandStatement) parent).getTarget();
if (target != null)
result.add(target);
Expression sep = ((ExpandStatement) parent).getSeparator();
if (sep != null)
result.add(sep);
}
// ExpressionStmt
else if (parent instanceof ExpressionStatement) {
result.add(new EvaluatedElementWrapper(parent));
result.add(((ExpressionStatement) parent).getExpression());
}
else if (parent instanceof Statement)
XpandLog.logInfo("Implementation error: Wanted to set Breakpoint for unknown statement: "
+ parent.getClass().getSimpleName());
else
result.addAll(super.getBody(parent));
return result;
}
@Override
protected ISyntaxElement findElementForPosition(final IResource resource,
final int position, final int line) {
ISyntaxElement rootElem = getContainingRootElement(resource, position);
if (rootElem == null)
return null;
// this is not body but is root element.
ISyntaxElement element = null;
List<ISyntaxElement> bodyElements = getBody(rootElem);
for (ISyntaxElement item : bodyElements) {
if (contains(item, position)) {
element = item;
break;
}
}
if (element == null)
return rootElem;
return getContainingElement((SyntaxElement) element, position);
}
@Override
protected ISyntaxElement getContainingElement(final SyntaxElement element,
final int position) {
if (!contains(element, position))
return null;
if (element instanceof ExpandStatement) {
return getContainingElementOfExpandStatement(
(ExpandStatement) element, position);
} else if (element instanceof ExpressionStatement) {
return getContainingElementOfExpressionStatement(
(ExpressionStatement) element, position);
} else if (element instanceof FileStatement)
return getContainingElementOfFileStatement((FileStatement) element,
position);
else if (element instanceof ForEachStatement)
return getContainingElementOfForEachStatement(
(ForEachStatement) element, position);
else if (element instanceof IfStatement)
return getContainingElementOfIfStatement((IfStatement) element,
position);
else if (element instanceof LetStatement)
return getContainingElementOfLetStatement((LetStatement) element,
position);
else if (element instanceof ProtectStatement)
return getContainingElementOfProtectStatement(
(ProtectStatement) element, position);
return super.getContainingElement(element, position);
}
private ISyntaxElement getContainingElementOfExpressionStatement(
final ExpressionStatement exprStatement, final int position) {
return getContainingElement(exprStatement.getExpression(), position);
}
private boolean contains(final ISyntaxElement elem, final int position) {
return elem.getStart() <= position && elem.getEnd() > position;
}
private ISyntaxElement getContainingElementOfExpandStatement(
final ExpandStatement expandStatement, final int position) {
List<SyntaxElement> children = new ArrayList<SyntaxElement>();
// children.addAll(expandStatement.getParametersAsList());
children.add(expandStatement.getTarget());
return getContainingChild(expandStatement, children, position);
}
private ISyntaxElement getContainingElementOfFileStatement(
final FileStatement fileStatement, final int position) {
List<SyntaxElement> children = new ArrayList<SyntaxElement>();
children.add(fileStatement.getTargetFileName());
children.addAll(fileStatement.getBodyAsList());
return getContainingChild(fileStatement, children, position);
}
private ISyntaxElement getContainingElementOfForEachStatement(
final ForEachStatement forStatement, final int position) {
List<SyntaxElement> children = new ArrayList<SyntaxElement>();
children.add(forStatement.getTarget());
children.add(forStatement.getSeparator());
children.addAll(forStatement.getBodyAsList());
return getContainingChild(forStatement, children, position);
}
private ISyntaxElement getContainingElementOfIfStatement(
final IfStatement ifStatement, final int position) {
List<SyntaxElement> children = new ArrayList<SyntaxElement>();
children.add(ifStatement.getCondition());
children.addAll(ifStatement.getBodyAsList());
children.add(ifStatement.getElseIf());
return getContainingChild(ifStatement, children, position);
}
private ISyntaxElement getContainingElementOfLetStatement(
final LetStatement letStatement, final int position) {
List<SyntaxElement> children = new ArrayList<SyntaxElement>();
children.add(letStatement.getVarValue());
children.addAll(letStatement.getBodyAsList());
return getContainingChild(letStatement, children, position);
}
private ISyntaxElement getContainingElementOfProtectStatement(
final ProtectStatement protStatement, final int position) {
List<SyntaxElement> children = new ArrayList<SyntaxElement>();
children.addAll(protStatement.getBodyAsList());
return getContainingChild(protStatement, children, position);
}
@Override
protected boolean isValidReturnElement(final ISyntaxElement element) {
if (element instanceof TextStatement)
return false;
if (element instanceof Statement)
return true;
return super.isValidReturnElement(element);
}
// -------------------------------------------------------------------------
private Image icon = null;
@Override
public Image getIcon() {
if (icon != null)
return icon;
IPath path = new Path("/icons/templatefile.gif");
InputStream is = null;
try {
is = FileLocator.openStream(XpandEditorPlugin.getDefault()
.getBundle(), path, false);
} catch (IOException e) {
}
if (is != null) {
final ImageData iData = new ImageData(is);
icon = new Image(Display.getCurrent(), iData);
return icon;
}
return null;
}
}