Skip to content

Commit ffcfd5d

Browse files
adrianocolatom-wolfe
authored andcommitted
Allowed dice rolls without roll times (eg: d6) (#17)
1 parent c0850a9 commit ffcfd5d

File tree

3 files changed

+70
-12
lines changed

3 files changed

+70
-12
lines changed

spec/parser/dice-parser.parseDice.spec.ts

+33
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,39 @@ import { MockLexer } from '../helpers';
66

77
describe('DiceParser', () => {
88
describe('parseDice', () => {
9+
it('can correctly parse a simple dice roll without roll times.', () => {
10+
const lexer = new MockLexer([
11+
new Token(TokenType.Identifier, 0, 'd'),
12+
new Token(TokenType.Number, 1, '6')
13+
]);
14+
const parser = new Parser.DiceParser(lexer);
15+
const result = new ParseResult();
16+
const dice = parser.parseDice(result);
17+
expect(result.errors.length).toBe(0);
18+
19+
expect(dice.type).toBe(NodeType.Dice);
20+
expect(dice.getChildCount()).toBe(2);
21+
expect(dice.getChild(0).type).toBe(NodeType.Number);
22+
expect(dice.getChild(0).getAttribute('value')).toBe(1);
23+
expect(dice.getChild(1).type).toBe(NodeType.DiceSides);
24+
expect(dice.getChild(1).getAttribute('value')).toBe(6);
25+
});
26+
it('can correctly parse a simple fate dice roll without roll times.', () => {
27+
const lexer = new MockLexer([
28+
new Token(TokenType.Identifier, 0, 'dF'),
29+
]);
30+
const parser = new Parser.DiceParser(lexer);
31+
const result = new ParseResult();
32+
const dice = parser.parseDice(result);
33+
expect(result.errors.length).toBe(0);
34+
35+
expect(dice.type).toBe(NodeType.Dice);
36+
expect(dice.getChildCount()).toBe(2);
37+
expect(dice.getChild(0).type).toBe(NodeType.Number);
38+
expect(dice.getChild(0).getAttribute('value')).toBe(1);
39+
expect(dice.getChild(1).type).toBe(NodeType.DiceSides);
40+
expect(dice.getChild(1).getAttribute('value')).toBe('fate');
41+
});
942
it('can correctly parse a simple dice roll with pre-parsed number.', () => {
1043
const lexer = new MockLexer([
1144
new Token(TokenType.Number, 0, '10'),

spec/parser/dice-parser.parseDiceRoll.spec.ts

+31-11
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,22 @@ describe('DiceParser', () => {
4040
expect(dice.getChild(1).type).toBe(NodeType.DiceSides);
4141
expect(dice.getChild(1).getAttribute('value')).toBe(6);
4242
});
43+
it('can correctly parse a simple dice roll without roll times.', () => {
44+
const lexer = new MockLexer([
45+
new Token(TokenType.Identifier, 0, 'd'),
46+
new Token(TokenType.Number, 1, '6')
47+
]);
48+
const parser = new Parser.DiceParser(lexer);
49+
const result = new Parser.ParseResult();
50+
const dice = parser.parseDiceRoll(result);
51+
expect(result.errors.length).toBe(0);
52+
expect(dice.type).toBe(NodeType.Dice);
53+
expect(dice.getChildCount()).toBe(2);
54+
expect(dice.getChild(0).type).toBe(NodeType.Number);
55+
expect(dice.getChild(0).getAttribute('value')).toBe(1);
56+
expect(dice.getChild(1).type).toBe(NodeType.DiceSides);
57+
expect(dice.getChild(1).getAttribute('value')).toBe(6);
58+
});
4359
it('can correctly parse a simple fate dice roll', () => {
4460
const lexer = new MockLexer([
4561
new Token(TokenType.Number, 0, '10'),
@@ -56,6 +72,21 @@ describe('DiceParser', () => {
5672
expect(dice.getChild(1).type).toBe(NodeType.DiceSides);
5773
expect(dice.getChild(1).getAttribute('value')).toBe('fate');
5874
});
75+
it('can correctly parse a simple fate dice roll without roll times', () => {
76+
const lexer = new MockLexer([
77+
new Token(TokenType.Identifier, 0, 'dF')
78+
]);
79+
const parser = new Parser.DiceParser(lexer);
80+
const result = new Parser.ParseResult();
81+
const dice = parser.parseDiceRoll(result);
82+
expect(result.errors.length).toBe(0);
83+
expect(dice.type).toBe(NodeType.Dice);
84+
expect(dice.getChildCount()).toBe(2);
85+
expect(dice.getChild(0).type).toBe(NodeType.Number);
86+
expect(dice.getChild(0).getAttribute('value')).toBe(1);
87+
expect(dice.getChild(1).type).toBe(NodeType.DiceSides);
88+
expect(dice.getChild(1).getAttribute('value')).toBe('fate');
89+
});
5990
it('can correctly parse a dice roll with a bracketed number', () => {
6091
const lexer = new MockLexer([
6192
new Token(TokenType.ParenthesisOpen, 0, '('),
@@ -100,17 +131,6 @@ describe('DiceParser', () => {
100131
expect(dice.getChild(1).type).toBe(NodeType.DiceSides);
101132
expect(dice.getChild(1).getAttribute('value')).toBe(6);
102133
});
103-
it('throws on missing roll times', () => {
104-
const lexer = new MockLexer([
105-
new Token(TokenType.Identifier, 0, 'd'),
106-
new Token(TokenType.Number, 1, '10')
107-
]);
108-
const parser = new Parser.DiceParser(lexer);
109-
110-
const result = new Parser.ParseResult();
111-
const dice = parser.parseDiceRoll(result);
112-
expect(result.errors.length).toBeGreaterThanOrEqual(1);
113-
});
114134
it('throws on missing dice value', () => {
115135
const lexer = new MockLexer([
116136
new Token(TokenType.Number, 0, '6'),

src/parser/dice-parser.class.ts

+6-1
Original file line numberDiff line numberDiff line change
@@ -96,7 +96,11 @@ export class DiceParser extends BasicParser {
9696
const token = this.lexer.peekNextToken();
9797
switch (token.type) {
9898
case TokenType.Identifier:
99-
root = this.parseFunction(result);
99+
if (token.value === 'd' || token.value === 'dF') {
100+
root = this.parseDice(result);
101+
} else {
102+
root = this.parseFunction(result);
103+
}
100104
break;
101105
case TokenType.ParenthesisOpen:
102106
root = this.parseBracketedExpression(result);
@@ -125,6 +129,7 @@ export class DiceParser extends BasicParser {
125129
switch (token.type) {
126130
case TokenType.Number: return this.parseNumber(result);
127131
case TokenType.ParenthesisOpen: return this.parseBracketedExpression(result);
132+
case TokenType.Identifier: return Ast.Factory.create(Ast.NodeType.Number).setAttribute('value', Number(1));
128133
default: this.errorToken(result, TokenType.Number, token);
129134
}
130135
}

0 commit comments

Comments
 (0)