Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -18,22 +18,26 @@
import org.metaborg.spoofax.shell.functions.AnalyzeFunction;
import org.metaborg.spoofax.shell.functions.EvaluateFunction;
import org.metaborg.spoofax.shell.functions.FailableFunction;
import org.metaborg.spoofax.shell.functions.FoldFunction;
import org.metaborg.spoofax.shell.functions.IFunctionFactory;
import org.metaborg.spoofax.shell.functions.InputFunction;
import org.metaborg.spoofax.shell.functions.OpenInputFunction;
import org.metaborg.spoofax.shell.functions.PTransformFunction;
import org.metaborg.spoofax.shell.functions.ParseFunction;
import org.metaborg.spoofax.shell.functions.PrettyPrintFunction;
import org.metaborg.spoofax.shell.functions.StyleFunction;
import org.metaborg.spoofax.shell.invoker.ICommandInvoker;
import org.metaborg.spoofax.shell.invoker.SpoofaxCommandInvoker;
import org.metaborg.spoofax.shell.output.AnalyzeResult;
import org.metaborg.spoofax.shell.output.EvaluateResult;
import org.metaborg.spoofax.shell.output.FoldResult;
import org.metaborg.spoofax.shell.output.IResult;
import org.metaborg.spoofax.shell.output.IResultFactory;
import org.metaborg.spoofax.shell.output.IResultVisitor;
import org.metaborg.spoofax.shell.output.ISpoofaxTermResult;
import org.metaborg.spoofax.shell.output.InputResult;
import org.metaborg.spoofax.shell.output.ParseResult;
import org.metaborg.spoofax.shell.output.PrintResult;
import org.metaborg.spoofax.shell.output.StyleResult;
import org.metaborg.spoofax.shell.output.TransformResult;
import org.metaborg.spoofax.shell.services.IEditorServices;
Expand Down Expand Up @@ -125,6 +129,12 @@ protected void bindFactories() {
.implement(
new TypeLiteral<FailableFunction<ISpoofaxTermResult<?>, EvaluateResult, IResult>>() {
}, EvaluateFunction.class)
.implement(
new TypeLiteral<FailableFunction<ISpoofaxTermResult<?>, FoldResult, IResult>>() {
}, FoldFunction.class)
.implement(
new TypeLiteral<FailableFunction<FoldResult, PrintResult, IResult>>() {
}, PrettyPrintFunction.class)
.implement(new TypeLiteral<FailableFunction<ParseResult, StyleResult, IResult>>() {
}, StyleFunction.class).build(IFunctionFactory.class));
// CHECKSTYLE.ON: LineLength
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -16,20 +16,20 @@
import org.metaborg.spoofax.shell.output.StyledText;

/**
* Adapter {@link IResultVisitor} interface for displaying results and errors. An implementation of
* {@link IDisplay} knows how to interpret the style information of a {@link StyledText} and display
* it appropriately.
* Adapter {@link IResultVisitor} interface for displaying results and errors.
* An implementation of {@link IDisplay} knows how to interpret the style
* information of a {@link StyledText} and display it appropriately.
*/
public interface IDisplay extends IResultVisitor {

/**
* Display the given {@link StyledText}. How the style information is interpreted depends on the
* client.
* Display the given {@link StyledText}. How the style information is
* interpreted depends on the client.
*
* @param text
* @param styledText
* The {@link StyledText} to display.
*/
void displayStyledText(StyledText text);
void displayStyledText(StyledText styledText);

@Override
default void visitMessage(StyledText message) {
Expand All @@ -54,8 +54,8 @@ default void visitFailure(FailResult errorResult) {
}

/**
* Highlights the {@link SourceRegion}s of the given {@link IMessage}s in the given source text
* with a red color and bold style.
* Highlights the {@link SourceRegion}s of the given {@link IMessage}s in
* the given source text with a red color and bold style.
*
* @param sourceText
* The source text that caused the failure.
Expand All @@ -64,8 +64,10 @@ default void visitFailure(FailResult errorResult) {
* @return The highlighted {@link StyledText}
*/
default StyledText highlightMessagesInSource(String sourceText, List<IMessage> messages) {
List<ISourceRegion> regions = messages.stream().map(IMessage::region)
.filter(Objects::nonNull).collect(Collectors.toList());
List<ISourceRegion> regions = messages.stream()
.map(IMessage::region)
.filter(Objects::nonNull)
.collect(Collectors.toList());
StyledText styled = new StyledText();
IStyle style = new Style(Color.RED, null, true, false, false, false);
styled.append(regions, style, sourceText);
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,106 @@
package org.metaborg.spoofax.shell.functions;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Stack;

import org.metaborg.core.source.ISourceRegion;
import org.metaborg.core.source.SourceRegion;
import org.metaborg.spoofax.shell.output.FailOrSuccessResult;
import org.metaborg.spoofax.shell.output.FoldResult;
import org.metaborg.spoofax.shell.output.IResult;
import org.metaborg.spoofax.shell.output.ISpoofaxTermResult;
import org.spoofax.interpreter.terms.IStrategoTerm;

/**
* Creates a {@link FoldResult} from a given {@link ISpoofaxTermResult}.
*/
public class FoldFunction implements FailableFunction<ISpoofaxTermResult<?>, FoldResult, IResult> {

/**
* Instantiate a {@link FoldFunction}.
* Explicit
*/
public FoldFunction() {
}

@Override
public FailOrSuccessResult<FoldResult, IResult> apply(ISpoofaxTermResult<?> input) {

Helper helper = new Helper();

try {
IStrategoTerm term = input.ast().get();

term.writeAsString(helper, IStrategoTerm.INFINITE);

List<ISourceRegion> out = new ArrayList<>(helper.outputRegions);

return FailOrSuccessResult.successful(new FoldResult(term, out));
} catch (IOException e) {
// should not happen
throw new RuntimeException(e);
}
}

/**
* Helper to wrap {@link IStrategoTerm#writeAsString}.
*
* As {@link IStrategoTerm#prettyPrint(org.spoofax.interpreter.terms.ITermPrinter)} is
* deprecated {@link IStrategoTerm#writeAsString(Appendable, int)} is used instead.
*
* As {@link FoldFunction} should be state-less a private static class is used over
* an anonymous class with members or single-length-arrays to contain the state within the
* method scope.
*
* The {@link #Helper} recognizes <tt>(</tt> and <tt>)</tt> and uses them to
* recognize structures.
*/
private static class Helper implements Appendable {

private Stack<Integer> regionStack = new Stack<>();
private List<ISourceRegion> outputRegions = new ArrayList<>();

private int index = 0;
private int lastSeqIndex = -1;

@Override
public Appendable append(CharSequence csq, int start, int end) throws IOException {
return this.append(csq.subSequence(start, end));
}

@Override
public Appendable append(char c) throws IOException {
switch (c) {
case '(':
regionStack.push(lastSeqIndex == -1 ? 0 : lastSeqIndex);
lastSeqIndex = -1;
break;
case ')':
int startOffset = regionStack.pop();
int endOffset = index;
outputRegions.add(new SourceRegion(startOffset, endOffset));
lastSeqIndex = -1;
break;
case ',':
break;
default:
if (lastSeqIndex == -1) {
lastSeqIndex = index;
}
break;
}
index++;
return this;
}

@Override
public Appendable append(CharSequence csq) throws IOException {
lastSeqIndex = index;
index += csq.length();
return this;
}
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,10 @@
import org.metaborg.spoofax.shell.output.AnalyzeResult;
import org.metaborg.spoofax.shell.output.EvaluateResult;
import org.metaborg.spoofax.shell.output.IResult;
import org.metaborg.spoofax.shell.output.ISpoofaxTermResult;
import org.metaborg.spoofax.shell.output.InputResult;
import org.metaborg.spoofax.shell.output.ParseResult;
import org.metaborg.spoofax.shell.output.PrintResult;
import org.metaborg.spoofax.shell.output.StyleResult;
import org.metaborg.spoofax.shell.output.TransformResult;

Expand Down Expand Up @@ -128,4 +130,16 @@ public FailableFunction<String, StyleResult, IResult> pStyleFunction() {
return parseFunction()
.kleisliCompose(functionFactory.createStyleFunction(project, lang));
}

/**
* Composes a {@link PrettyPrintFunction}, which provides pretty printing.
*
* @return {@link PrettyPrintFunction} - The pretty print function.
*/
public FailableFunction<ISpoofaxTermResult<?>, PrintResult, IResult> termPrettyPrintFunction() {
return functionFactory.createFoldFunction(project, lang)
.kleisliCompose(functionFactory.createPrettyPrintFunction(project, lang));

}

}
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,12 @@
import org.metaborg.spoofax.shell.commands.IReplCommand;
import org.metaborg.spoofax.shell.output.AnalyzeResult;
import org.metaborg.spoofax.shell.output.EvaluateResult;
import org.metaborg.spoofax.shell.output.FoldResult;
import org.metaborg.spoofax.shell.output.IResult;
import org.metaborg.spoofax.shell.output.ISpoofaxTermResult;
import org.metaborg.spoofax.shell.output.InputResult;
import org.metaborg.spoofax.shell.output.ParseResult;
import org.metaborg.spoofax.shell.output.PrintResult;
import org.metaborg.spoofax.shell.output.StyleResult;
import org.metaborg.spoofax.shell.output.TransformResult;

Expand Down Expand Up @@ -101,6 +103,25 @@ public interface IFunctionFactory {
FailableFunction<ParseResult, StyleResult, IResult>
createStyleFunction(IProject project, ILanguageImpl lang);

/**
* Factory method for creating a {@link FoldFunction}.
* @param project The associated {@link IProject}
* @param lang The associated {@link ILanguageImpl}
* @return an {@link FoldFunction}
*/
FailableFunction<ISpoofaxTermResult<?>, FoldResult, IResult>
createFoldFunction(IProject project, ILanguageImpl lang);

/**
* Factory method for creating a {@link PrettyPrintFunction}.
* @param project The associated {@link IProject}
* @param lang The associated {@link ILanguageImpl}
* @return an {@link PrettyPrintFunction}
*/
FailableFunction<FoldResult, PrintResult, IResult>
createPrettyPrintFunction(IProject project, ILanguageImpl lang);


/**
* Factory method for creating a {@link CommandBuilder}.
* The {@link CommandBuilder} composes an {@link IReplCommand}
Expand Down
Loading