cbc/net/loveruby/cflat/ast/CflatToken.java

100 lines
2.5 KiB
Java

package net.loveruby.cflat.ast;
import net.loveruby.cflat.parser.Token;
import net.loveruby.cflat.parser.ParserConstants;
import net.loveruby.cflat.utils.TextUtils;
import java.util.*;
/**
* Token wrapper.
*/
public class CflatToken implements Iterable<CflatToken> {
protected Token token;
protected boolean isSpecial;
public CflatToken(Token token) {
this(token, false);
}
public CflatToken(Token token, boolean isSpecial) {
this.token = token;
this.isSpecial = isSpecial;
}
public String toString() {
return token.image;
}
public boolean isSpecial() {
return this.isSpecial;
}
public int kindID() {
return token.kind;
}
public String kindName() {
return ParserConstants.tokenImage[token.kind];
}
public int lineno() {
return token.beginLine;
}
public int column() {
return token.beginColumn;
}
public String image() {
return token.image;
}
public String dumpedImage() {
return TextUtils.dumpString(token.image);
}
public Iterator<CflatToken> iterator() {
return buildTokenList(token, false).iterator();
}
protected List<CflatToken> tokensWithoutFirstSpecials() {
return buildTokenList(token, true);
}
protected List<CflatToken> buildTokenList(Token first, boolean rejectFirstSpecials) {
List<CflatToken> result = new ArrayList<CflatToken>();
boolean rejectSpecials = rejectFirstSpecials;
for (Token t = first; t != null; t = t.next) {
if (t.specialToken != null && !rejectSpecials) {
Token s = specialTokenHead(t.specialToken);
for (; s != null; s = s.next) {
result.add(new CflatToken(s));
}
}
result.add(new CflatToken(t));
rejectSpecials = false;
}
return result;
}
protected Token specialTokenHead(Token firstSpecial) {
Token s = firstSpecial;
while (s.specialToken != null) {
s = s.specialToken;
}
return s;
}
public String includedLine() {
StringBuffer buf = new StringBuffer();
for (CflatToken t : tokensWithoutFirstSpecials()) {
int idx = t.image().indexOf("\n");
if (idx >= 0) {
buf.append(t.image().substring(0, idx));
break;
}
buf.append(t.image());
}
return buf.toString();
}
}