88#include < scratchcpp/block.h>
99#include < scratchcpp/input.h>
1010#include < scratchcpp/field.h>
11+ #include < scratchcpp/monitor.h>
1112#include < scratchcpp/executioncontext.h>
1213#include < scratchcpp/executablecode.h>
1314#include < enginemock.h>
1415#include < randomgeneratormock.h>
16+ #include < monitorhandlermock.h>
1517
1618#include " ../common.h"
1719#include " util.h"
@@ -21,6 +23,8 @@ using namespace libscratchcpp;
2123using namespace libscratchcpp ::test;
2224
2325using ::testing::Return;
26+ using ::testing::Invoke;
27+ using ::testing::_;
2428
2529class ListBlocksTest : public testing ::Test
2630{
@@ -40,6 +44,81 @@ class ListBlocksTest : public testing::Test
4044 RandomGeneratorMock m_rng;
4145};
4246
47+ TEST_F (ListBlocksTest, ListContents)
48+ {
49+ auto target = std::make_shared<Sprite>();
50+ auto list1 = std::make_shared<List>(" " , " " );
51+ target->addList (list1);
52+ auto list2 = std::make_shared<List>(" " , " " );
53+ target->addList (list2);
54+
55+ list1->append (1 );
56+ list1->append (2 );
57+ list1->append (4 );
58+
59+ list2->append (" Lorem" );
60+ list2->append (" ipsum" );
61+ list2->append (" dolor" );
62+ list2->append (" sit" );
63+ list2->append (" amet" );
64+
65+ ScriptBuilder builder (m_extension.get (), m_engine, target);
66+
67+ builder.addBlock (" data_listcontents" );
68+ builder.addEntityField (" LIST" , list1);
69+ builder.captureBlockReturnValue ();
70+
71+ builder.addBlock (" data_listcontents" );
72+ builder.addEntityField (" LIST" , list2);
73+ builder.captureBlockReturnValue ();
74+
75+ builder.build ();
76+
77+ builder.run ();
78+ List *list = builder.capturedValues ();
79+ ValueData *data = list->data ();
80+ ASSERT_EQ (list->size (), 2 );
81+ ASSERT_EQ (Value (data[0 ]).toString (), " 124" );
82+ ASSERT_EQ (Value (data[1 ]).toString (), " Lorem ipsum dolor sit amet" );
83+ }
84+
85+ TEST_F (ListBlocksTest, ListMonitor)
86+ {
87+ auto target = std::make_shared<Sprite>();
88+ auto list1 = std::make_shared<List>(" " , " list1" );
89+ target->addList (list1);
90+ auto list2 = std::make_shared<List>(" " , " list2" );
91+ target->addList (list2);
92+
93+ MonitorHandlerMock iface1, iface2;
94+ EXPECT_CALL (iface1, init);
95+ EXPECT_CALL (iface2, init);
96+
97+ auto monitor1 = std::make_shared<Monitor>(" monitor" , " data_listcontents" );
98+ auto monitor2 = std::make_shared<Monitor>(" monitor" , " data_listcontents" );
99+ monitor1->block ()->setTarget (target.get ());
100+ monitor1->setInterface (&iface1);
101+ monitor2->block ()->setTarget (target.get ());
102+ monitor2->setInterface (&iface2);
103+ m_engine->setMonitors ({ monitor1, monitor2 });
104+
105+ ScriptBuilder builder1 (m_extension.get (), m_engine, target);
106+ builder1.addBlock (monitor1->block ());
107+ builder1.addEntityField (" LIST" , list1);
108+
109+ ScriptBuilder builder2 (m_extension.get (), m_engine, target);
110+ builder2.addBlock (monitor2->block ());
111+ builder2.addEntityField (" LIST" , list2);
112+
113+ m_engine->compile ();
114+ ASSERT_EQ (monitor1->name (), list1->name ());
115+ ASSERT_EQ (monitor2->name (), list2->name ());
116+
117+ EXPECT_CALL (iface1, onValueChanged (_)).WillOnce (Invoke ([list1](const Value &value) { ASSERT_EQ (value.toDouble (), (uintptr_t )list1.get ()); }));
118+ EXPECT_CALL (iface2, onValueChanged (_)).WillOnce (Invoke ([list2](const Value &value) { ASSERT_EQ (value.toDouble (), (uintptr_t )list2.get ()); }));
119+ m_engine->updateMonitors ();
120+ }
121+
43122TEST_F (ListBlocksTest, AddToList)
44123{
45124 auto target = std::make_shared<Sprite>();
0 commit comments