Skip to content

Commit

Permalink
test(jenny): Add testScenario() test method (#2147)
Browse files Browse the repository at this point in the history
Add testScenario() method for jenny, allowing to test different dialogues more easily. This is the same system as used by YarnSpinner, so that we can verify that language features are working the same way.

Some of the testplans from YarnSpinner were ported, though many of them are marked as skip=true. This gives us an opportunity to try TDD.
  • Loading branch information
st-pasha authored Nov 6, 2022
1 parent cbfa789 commit f6432c6
Show file tree
Hide file tree
Showing 11 changed files with 593 additions and 15 deletions.
7 changes: 6 additions & 1 deletion packages/flame_jenny/jenny/lib/src/parse/parse.dart
Original file line number Diff line number Diff line change
Expand Up @@ -274,7 +274,7 @@ class _Parser {
position += 1;
syntaxError('this command is only allowed after an <<if>>');
} else {
assert(token.isCommand);
assert(token.isCommand, 'unimplemented $token');
return parseUserDefinedCommand();
}
}
Expand Down Expand Up @@ -360,6 +360,7 @@ class _Parser {
// TODO(st-pasha): add verification for node existence at the end of
// project setup
target = StringLiteral(token.content);
position += 1;
} else {
take(Token.startExpression);
final expression = parseExpression();
Expand All @@ -371,13 +372,15 @@ class _Parser {
}
}
take(Token.endCommand);
take(Token.newline);
return JumpCommand(target);
}

Command parseCommandStop() {
take(Token.startCommand);
take(Token.commandStop);
take(Token.endCommand);
take(Token.newline);
return const StopCommand();
}

Expand All @@ -389,6 +392,7 @@ class _Parser {
typeError('<<wait>> command expects a numeric argument');
}
take(Token.endCommand);
take(Token.newline);
return WaitCommand(expression as NumExpression);
}

Expand Down Expand Up @@ -437,6 +441,7 @@ class _Parser {
throw UnimplementedError();
}
take(Token.endCommand);
take(Token.newline);
return SetCommand(variableName, expression);
}

Expand Down
135 changes: 123 additions & 12 deletions packages/flame_jenny/jenny/test/dialogue_runner_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -3,24 +3,28 @@ import 'dart:async';
import 'package:jenny/jenny.dart';
import 'package:test/test.dart';

import 'test_scenario.dart';
import 'utils.dart';

void main() {
group('DialogueRunner', () {
test('plain dialogue', () async {
final yarn = YarnProject()
..parse('title: Hamlet\n'
'---\n'
"Bernardo: Who's there?\n"
'Francisco: Nay, answer me. Stand and unfold yourself.\n'
'Bernardo: Long live the King!\n'
'Francisco: Bernardo?\n'
'Bernardo: He\n'
'Francisco: You come most carefully upon your hour.\n'
"Bernardo: 'Tis now struck twelve. Get thee to bed, Francisco.\n"
"Francisco: For this relief much thanks. 'Tis bitter cold, "
'And I am sick at heart.\n'
'===\n');
..parse(
'-------------\n'
'title: Hamlet\n'
'-------------\n'
"Bernardo: Who's there?\n"
'Francisco: Nay, answer me. Stand and unfold yourself.\n'
'Bernardo: Long live the King!\n'
'Francisco: Bernardo?\n'
'Bernardo: He\n'
'Francisco: You come most carefully upon your hour.\n'
"Bernardo: 'Tis now struck twelve. Get thee to bed, Francisco.\n"
"Francisco: For this relief much thanks. 'Tis bitter cold, "
'And I am sick at heart.\n'
'===\n',
);
final view = _RecordingDialogueView();
final dialogue = DialogueRunner(yarnProject: yarn, dialogueViews: [view]);
await dialogue.runNode('Hamlet');
Expand Down Expand Up @@ -193,6 +197,113 @@ void main() {
),
);
});

testScenario(
testName: 'Example.plan',
input: '''
title: Start
tags:
colorID: 0
position: 592,181
---
A: Hey, I'm a character in a script!
B: And I am too! You are talking to me!
-> What's going on
A: Why this is a demo of the script system!
B: And you're in it!
-> Um ok
A: How delightful!
B: What would you prefer to do next?
-> Leave
<<jump Leave>>
-> Learn more
<<jump LearnMore>>
===
title: Leave
tags:
colorID: 0
position: 387,487
---
A: Oh, goodbye!
B: You'll be back soon!
===
title: LearnMore
tags: rawText
colorID: 0
position: 763,472
---
A: HAHAHA
===''',
testPlan: '''
line: A: Hey, I'm a character in a script!
line: B: And I am too! You are talking to me!
option: What's going on
option: Um ok
select: 1
line: A: Why this is a demo of the script system!
line: B: And you're in it!
line: A: How delightful!
line: B: What would you prefer to do next?
option: Leave
option: Learn more
select: 1
line: A: Oh, goodbye!
line: B: You'll be back soon!
''',
);

testScenario(
testName: 'Compiler.plan',
input: r'''
title: Start
---
// Compiler tests
This is a line!
<<if false>>
What what this is also a line!
<<endif>>
<<this is a custom command>>
<<set $foo to 1+2>>
<<if $foo is 3>>
Foo is 3!
<<elseif $foo is 4>>
Foo is 4!
<<else>>
Foo is something TOTALLY DIFFERENT.
<<endif>>
-> This is a shortcut option that you'll never see <<if false>>
Nice.
-> This is a different shortcut option
Sweet, but what about this?
-> It's ok
Cool.
-> Huh?
-> This is a shortcut option with no consequential text.
All done with the shortcut options!
===
''',
testPlan: '''
line: This is a line!
line: Foo is 3!
option: This is a shortcut option that you'll never see [disabled]
option: This is a different shortcut option
option: This is a shortcut option with no consequential text.
select: 2
line: Sweet, but what about this?
option: It's ok
option: Huh?
select: 1
line: Cool.
line: All done with the shortcut options!
''',
skip: true,
);
});
}

Expand Down
12 changes: 12 additions & 0 deletions packages/flame_jenny/jenny/test/parse/tokenize_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -704,6 +704,18 @@ void main() {
);
});

test('unicode variable names', () {
expect(
() => tokenize('---\n---\n'
'{ \$эксперимент }\n'
'===\n'),
hasSyntaxError('SyntaxError: invalid variable name\n'
'> at line 3 column 3:\n'
'> { \$эксперимент }\n'
'> ^\n'),
);
});

test('invalid string', () {
expect(
() => tokenize('---\n---\n'
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import 'package:test/test.dart';

import '../../test_scenario.dart';

void main() {
group('IfCommand', () {
testScenario(
testName: 'IfStatements.yarn',
input: '''
title: Start
---
<<if true>>
Player: Hey, Sally. #line:794945
Sally: Oh! Hi. #line:2dc39b
Sally: You snuck up on me. #line:34de2f
Sally: Don't do that. #line:dcc2bc
<<else>>
Player: Hey. #line:a8e70c
Sally: Hi. #line:305cde
<<endif>>
===
''',
testPlan: '''
line: Player: Hey, Sally.
line: Sally: Oh! Hi.
line: Sally: You snuck up on me.
line: Sally: Don't do that.
''',
);
});
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
import 'package:test/test.dart';

import '../../test_scenario.dart';

void main() {
group('SetCommand', () {
testScenario(
testName: 'AnalysisTest.plan',
input: r'''
title: Start
---
// testing
<<declare $foo = 0>> // used
<<declare $bar = 0>> // written to but never read
<<set $foo to 1>>
<<set $bar to $foo>>
{$foo} {$bar}
===
''',
testPlan: 'line: 1 1',
skip: true,
);

testScenario(
testName: 'Basic.plan',
input: r'''
title: Start
---
whoa what here's some text
<<set $foo to (1+3*3/9)-1>>
<<if $foo is 1>> // testing a comment
this should appear :)
<<if 1 is 1>>
NESTED IF BLOCK WHAAAT
<<set $foo += 47 + 6>>
<<endif>>
<<else>>
oh noooo it didn't work :(
<<endif>>
<<if $foo is 54>>
haha nice now 'set' works even when deeply nested
<<else>>
aaargh :(
<<endif>>
===
''',
testPlan: '''
line: whoa what here's some text
line: this should appear :)
line: NESTED IF BLOCK WHAAAT
line: haha nice now 'set' works even when deeply nested
''',
skip: true,
);
});
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
import 'package:test/test.dart';

import '../../test_scenario.dart';

void main() {
group('UserDefinedCommand', () {
testScenario(
testName: 'Commands.yarn',
input: '''
title: Start
---
// Testing commands
<<flip Harley3 +1>>
// Commands that begin with keywords
<<toggle>>
<<settings>>
<<iffy>>
<<nulled>>
<<orion>>
<<andorian>>
<<note>>
<<isActive>>
// Commands with a single character
<<p>>
// Commands with colons
<<hide Collision:GermOnPorch>>
===
''',
testPlan: '''
command: flip Harley3 +1
command: toggle
command: settings
command: iffy
command: nulled
command: orion
command: andorian
command: note
command: isActive
command: p
command: hide Collision:GermOnPorch
''',
skip: true,
);
});
}
Loading

0 comments on commit f6432c6

Please sign in to comment.