Skip to content

Commit 984f7bf

Browse files
committed
Add Engine test
1 parent a648db7 commit 984f7bf

File tree

5 files changed

+319
-0
lines changed

5 files changed

+319
-0
lines changed

test/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,3 +27,4 @@ add_subdirectory(scratchconfiguration)
2727
add_subdirectory(assets)
2828
add_subdirectory(script)
2929
add_subdirectory(extensions)
30+
add_subdirectory(engine)

test/engine/CMakeLists.txt

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
add_executable(
2+
engine_test
3+
engine_test.cpp
4+
testsection.cpp
5+
testsection.h
6+
)
7+
8+
target_link_libraries(
9+
engine_test
10+
GTest::gtest_main
11+
scratchcpp
12+
)
13+
14+
gtest_discover_tests(engine_test)

test/engine/engine_test.cpp

Lines changed: 274 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,274 @@
1+
#include <scratchcpp/broadcast.h>
2+
#include <scratchcpp/block.h>
3+
#include <engine/engine.h>
4+
5+
#include "../common.h"
6+
#include "testsection.h"
7+
8+
using namespace libscratchcpp;
9+
10+
// NOTE: resolveIds() and compile() are tested in load_project_test
11+
12+
TEST(EngineTest, Clear)
13+
{
14+
Engine engine;
15+
16+
auto target1 = std::make_shared<Target>();
17+
auto target2 = std::make_shared<Target>();
18+
engine.setTargets({ target1, target2 });
19+
20+
auto broadcast1 = std::make_shared<Broadcast>("", "");
21+
auto broadcast2 = std::make_shared<Broadcast>("", "");
22+
engine.setBroadcasts({ broadcast1, broadcast2 });
23+
24+
auto section = std::make_shared<TestSection>();
25+
engine.registerSection(section);
26+
27+
engine.clear();
28+
ASSERT_TRUE(engine.targets().empty());
29+
ASSERT_TRUE(engine.broadcasts().empty());
30+
ASSERT_TRUE(engine.registeredSections().empty());
31+
}
32+
33+
TEST(EngineTest, BreakFrame)
34+
{
35+
Engine engine;
36+
ASSERT_FALSE(engine.breakingCurrentFrame());
37+
38+
engine.breakFrame();
39+
ASSERT_TRUE(engine.breakingCurrentFrame());
40+
}
41+
42+
TEST(EngineTest, Sections)
43+
{
44+
Engine engine;
45+
46+
auto section1 = std::make_shared<TestSection>();
47+
engine.registerSection(section1);
48+
49+
auto section2 = std::make_shared<TestSection>();
50+
engine.registerSection(section2);
51+
52+
engine.registerSection(section1); // register existing section
53+
54+
ASSERT_EQ(engine.registeredSections().size(), 2);
55+
if (engine.registeredSections()[0] == section1)
56+
ASSERT_EQ(engine.registeredSections()[1].get(), section2.get());
57+
else {
58+
ASSERT_EQ(engine.registeredSections()[0].get(), section2.get());
59+
ASSERT_EQ(engine.registeredSections()[1].get(), section1.get());
60+
}
61+
}
62+
63+
unsigned int testFunction1(VirtualMachine *)
64+
{
65+
return 0;
66+
}
67+
68+
unsigned int testFunction2(VirtualMachine *)
69+
{
70+
return 0;
71+
}
72+
73+
TEST(EngineTest, Functions)
74+
{
75+
Engine engine;
76+
77+
ASSERT_EQ(engine.functionIndex(&testFunction1), 0);
78+
ASSERT_EQ(engine.functionIndex(&testFunction2), 1);
79+
ASSERT_EQ(engine.functionIndex(&testFunction1), 0);
80+
ASSERT_EQ(engine.functionIndex(&testFunction2), 1);
81+
}
82+
83+
void compileTest1(Compiler *)
84+
{
85+
}
86+
87+
void compileTest2(Compiler *)
88+
{
89+
}
90+
91+
TEST(EngineTest, CompileFunctions)
92+
{
93+
Engine engine;
94+
95+
auto section1 = std::make_shared<TestSection>();
96+
engine.registerSection(section1);
97+
auto container1 = engine.blockSectionContainer(section1.get());
98+
99+
auto section2 = std::make_shared<TestSection>();
100+
engine.registerSection(section2);
101+
auto container2 = engine.blockSectionContainer(section2.get());
102+
103+
TestSection section3;
104+
105+
engine.addCompileFunction(section1.get(), "test1", &compileTest1);
106+
engine.addCompileFunction(section2.get(), "test2", &compileTest2);
107+
engine.addCompileFunction(section1.get(), "test1", &compileTest1);
108+
engine.addCompileFunction(&section3, "test1", &compileTest1);
109+
110+
ASSERT_EQ(container1->resolveBlockCompileFunc("test1"), &compileTest1);
111+
ASSERT_EQ(container1->resolveBlockCompileFunc("test2"), nullptr);
112+
ASSERT_EQ(container2->resolveBlockCompileFunc("test1"), nullptr);
113+
ASSERT_EQ(container2->resolveBlockCompileFunc("test2"), &compileTest2);
114+
}
115+
116+
TEST(EngineTest, HatBlocks)
117+
{
118+
Engine engine;
119+
120+
auto section1 = std::make_shared<TestSection>();
121+
engine.registerSection(section1);
122+
auto container1 = engine.blockSectionContainer(section1.get());
123+
124+
auto section2 = std::make_shared<TestSection>();
125+
engine.registerSection(section2);
126+
auto container2 = engine.blockSectionContainer(section2.get());
127+
128+
TestSection section3;
129+
130+
engine.addHatBlock(section1.get(), "test1");
131+
engine.addHatBlock(section2.get(), "test2");
132+
engine.addHatBlock(section1.get(), "test1");
133+
engine.addHatBlock(&section3, "test1");
134+
135+
ASSERT_NE(container1->resolveBlockCompileFunc("test1"), nullptr);
136+
ASSERT_EQ(container1->resolveBlockCompileFunc("test2"), nullptr);
137+
ASSERT_EQ(container2->resolveBlockCompileFunc("test1"), nullptr);
138+
ASSERT_NE(container2->resolveBlockCompileFunc("test2"), nullptr);
139+
}
140+
141+
TEST(EngineTest, Inputs)
142+
{
143+
Engine engine;
144+
145+
auto section1 = std::make_shared<TestSection>();
146+
engine.registerSection(section1);
147+
auto container1 = engine.blockSectionContainer(section1.get());
148+
149+
auto section2 = std::make_shared<TestSection>();
150+
engine.registerSection(section2);
151+
auto container2 = engine.blockSectionContainer(section2.get());
152+
153+
TestSection section3;
154+
155+
engine.addInput(section1.get(), "VALUE1", 1);
156+
engine.addInput(section2.get(), "VALUE2", 2);
157+
engine.addInput(section1.get(), "VALUE1", 3); // change ID of existing input
158+
engine.addInput(&section3, "VALUE3", 4);
159+
160+
ASSERT_EQ(container1->resolveInput("VALUE1"), 3);
161+
ASSERT_EQ(container1->resolveInput("VALUE2"), -1);
162+
ASSERT_EQ(container1->resolveInput("VALUE3"), -1);
163+
ASSERT_EQ(container2->resolveInput("VALUE1"), -1);
164+
ASSERT_EQ(container2->resolveInput("VALUE2"), 2);
165+
ASSERT_EQ(container2->resolveInput("VALUE3"), -1);
166+
}
167+
168+
TEST(EngineTest, Fields)
169+
{
170+
Engine engine;
171+
172+
auto section1 = std::make_shared<TestSection>();
173+
engine.registerSection(section1);
174+
auto container1 = engine.blockSectionContainer(section1.get());
175+
176+
auto section2 = std::make_shared<TestSection>();
177+
engine.registerSection(section2);
178+
auto container2 = engine.blockSectionContainer(section2.get());
179+
180+
TestSection section3;
181+
182+
engine.addField(section1.get(), "VALUE1", 1);
183+
engine.addField(section2.get(), "VALUE2", 2);
184+
engine.addField(section1.get(), "VALUE1", 3); // change ID of existing field
185+
engine.addField(&section3, "VALUE3", 4);
186+
187+
ASSERT_EQ(container1->resolveField("VALUE1"), 3);
188+
ASSERT_EQ(container1->resolveField("VALUE2"), -1);
189+
ASSERT_EQ(container1->resolveField("VALUE3"), -1);
190+
ASSERT_EQ(container2->resolveField("VALUE1"), -1);
191+
ASSERT_EQ(container2->resolveField("VALUE2"), 2);
192+
ASSERT_EQ(container2->resolveField("VALUE3"), -1);
193+
}
194+
195+
TEST(EngineTest, FieldValues)
196+
{
197+
Engine engine;
198+
199+
auto section1 = std::make_shared<TestSection>();
200+
engine.registerSection(section1);
201+
auto container1 = engine.blockSectionContainer(section1.get());
202+
203+
auto section2 = std::make_shared<TestSection>();
204+
engine.registerSection(section2);
205+
auto container2 = engine.blockSectionContainer(section2.get());
206+
207+
TestSection section3;
208+
209+
engine.addFieldValue(section1.get(), "value1", 1);
210+
engine.addFieldValue(section2.get(), "value2", 2);
211+
engine.addFieldValue(section1.get(), "value1", 3); // change ID of existing field
212+
engine.addFieldValue(&section3, "value3", 4);
213+
214+
ASSERT_EQ(container1->resolveFieldValue("value1"), 3);
215+
ASSERT_EQ(container1->resolveFieldValue("value2"), -1);
216+
ASSERT_EQ(container1->resolveFieldValue("value3"), -1);
217+
ASSERT_EQ(container2->resolveFieldValue("value1"), -1);
218+
ASSERT_EQ(container2->resolveFieldValue("value2"), 2);
219+
ASSERT_EQ(container2->resolveFieldValue("value3"), -1);
220+
}
221+
222+
TEST(EngineTest, Broadcasts)
223+
{
224+
Engine engine;
225+
ASSERT_TRUE(engine.broadcasts().empty());
226+
227+
auto b1 = std::make_shared<Broadcast>("a", "message1");
228+
auto b2 = std::make_shared<Broadcast>("b", "message2");
229+
auto b3 = std::make_shared<Broadcast>("c", "Test");
230+
engine.setBroadcasts({ b1, b2, b3 });
231+
232+
ASSERT_EQ(engine.broadcasts(), std::vector<std::shared_ptr<Broadcast>>({ b1, b2, b3 }));
233+
ASSERT_EQ(engine.broadcastAt(0), b1);
234+
ASSERT_EQ(engine.broadcastAt(1), b2);
235+
ASSERT_EQ(engine.broadcastAt(2), b3);
236+
ASSERT_EQ(engine.broadcastAt(3), nullptr);
237+
ASSERT_EQ(engine.broadcastAt(-1), nullptr);
238+
239+
ASSERT_EQ(engine.findBroadcast("invalid"), -1);
240+
ASSERT_EQ(engine.findBroadcast("message1"), 0);
241+
ASSERT_EQ(engine.findBroadcast("message2"), 1);
242+
ASSERT_EQ(engine.findBroadcast("Test"), 2);
243+
244+
ASSERT_EQ(engine.findBroadcastById("d"), -1);
245+
ASSERT_EQ(engine.findBroadcastById("a"), 0);
246+
ASSERT_EQ(engine.findBroadcastById("b"), 1);
247+
ASSERT_EQ(engine.findBroadcastById("c"), 2);
248+
}
249+
250+
TEST(EngineTest, Targets)
251+
{
252+
Engine engine;
253+
ASSERT_TRUE(engine.targets().empty());
254+
255+
auto t1 = std::make_shared<Target>();
256+
t1->setName("Sprite1");
257+
auto t2 = std::make_shared<Target>();
258+
t2->setName("Sprite2");
259+
auto t3 = std::make_shared<Target>();
260+
t3->setName("Stage");
261+
engine.setTargets({ t1, t2, t3 });
262+
263+
ASSERT_EQ(engine.targets(), std::vector<std::shared_ptr<Target>>({ t1, t2, t3 }));
264+
ASSERT_EQ(engine.targetAt(0), t1.get());
265+
ASSERT_EQ(engine.targetAt(1), t2.get());
266+
ASSERT_EQ(engine.targetAt(2), t3.get());
267+
ASSERT_EQ(engine.targetAt(3), nullptr);
268+
ASSERT_EQ(engine.targetAt(-1), nullptr);
269+
270+
ASSERT_EQ(engine.findTarget("invalid"), -1);
271+
ASSERT_EQ(engine.findTarget("Sprite1"), 0);
272+
ASSERT_EQ(engine.findTarget("Sprite2"), 1);
273+
ASSERT_EQ(engine.findTarget("Stage"), 2);
274+
}

test/engine/testsection.cpp

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
#include <scratchcpp/iengine.h>
2+
3+
#include "testsection.h"
4+
5+
using namespace libscratchcpp;
6+
7+
std::string TestSection::name() const
8+
{
9+
return "Test";
10+
}
11+
12+
void TestSection::registerBlocks(IEngine *engine)
13+
{
14+
}

test/engine/testsection.h

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
#pragma once
2+
3+
#include <scratchcpp/iblocksection.h>
4+
5+
namespace libscratchcpp
6+
{
7+
8+
class TestSection : public IBlockSection
9+
{
10+
public:
11+
std::string name() const override;
12+
13+
void registerBlocks(IEngine *engine) override;
14+
};
15+
16+
} // namespace libscratchcpp

0 commit comments

Comments
 (0)