TEST(ConnectionList, MoveAssignmentOperator) { Signal<void(std::string)> nameChanged; std::string name; ConnectionList connections1; { ConnectionList connections2; connections2 += nameChanged.Connect([&](std::string const& n) { name = n; }); nameChanged("alice"); EXPECT_EQ("alice", name); connections1 = std::move(connections2); nameChanged("bob"); EXPECT_EQ("bob", name); connections2.Disconnect(); nameChanged("chuck"); EXPECT_EQ("chuck", name); } nameChanged("norris"); EXPECT_EQ("norris", name); connections1.Disconnect(); nameChanged("gates"); EXPECT_EQ("norris", name); }
TEST(lagi_signal, basic) { Signal<> s; int x = 0; Connection c = s.Connect(increment(x)); EXPECT_EQ(0, x); s(); EXPECT_EQ(1, x); }
TEST(lagi_signal, basic) { Signal<> s; int x = 0; Connection c = s.Connect([&] { ++x; }); EXPECT_EQ(0, x); s(); EXPECT_EQ(1, x); }
TEST(lagi_signal, multiple) { Signal<> s; int x = 0; Connection c1 = s.Connect(increment(x)); Connection c2 = s.Connect(increment(x)); EXPECT_EQ(0, x); s(); EXPECT_EQ(2, x); }
TEST(lagi_signal, multiple) { Signal<> s; int x = 0; Connection c1 = s.Connect([&] { ++x; }); Connection c2 = s.Connect([&] { ++x; }); EXPECT_EQ(0, x); s(); EXPECT_EQ(2, x); }
TEST(lagi_signal, manual_disconnect) { Signal<> s; int x = 0; Connection c1 = s.Connect([&] { ++x; }); EXPECT_EQ(0, x); s(); EXPECT_EQ(1, x); c1.Disconnect(); s(); EXPECT_EQ(1, x); }
TEST(lagi_signal, manual_disconnect) { Signal<> s; int x = 0; Connection c1 = s.Connect(increment(x)); EXPECT_EQ(0, x); s(); EXPECT_EQ(1, x); c1.Disconnect(); s(); EXPECT_EQ(1, x); }
TEST(lagi_signal, one_arg) { Signal<int> s; int x = 0; Connection c = s.Connect(increment(x)); s(0); EXPECT_EQ(0, x); s(10); EXPECT_EQ(10, x); s(20); EXPECT_EQ(30, x); }
TEST(lagi_signal, one_arg) { Signal<int> s; int x = 0; Connection c = s.Connect([&](int v) { x += v; }); s(0); EXPECT_EQ(0, x); s(10); EXPECT_EQ(10, x); s(20); EXPECT_EQ(30, x); }
TEST(lagi_signal, connection_outlives_slot) { int x = 0; Connection c; EXPECT_EQ(0, x); { Signal<> s; c = s.Connect([&] { ++x; }); s(); EXPECT_EQ(1, x); } c.Disconnect(); }
TEST(lagi_signal, auto_disconnect) { Signal<> s; int x = 0; EXPECT_EQ(0, x); { Connection c = s.Connect([&] { ++x; }); s(); EXPECT_EQ(1, x); } s(); EXPECT_EQ(1, x); }
TEST(lagi_signal, auto_disconnect) { Signal<> s; int x = 0; EXPECT_EQ(0, x); { Connection c = s.Connect(increment(x)); s(); EXPECT_EQ(1, x); } s(); EXPECT_EQ(1, x); }
template <typename...Arguments, typename Func> POMDOG_EXPORT Connection ConnectSingleShot(Signal<void(Arguments...)> & signal, Func && func) { auto connection = std::make_shared<Connection>(); *connection = signal.Connect([ conn = connection, func = std::forward<Func>(func) ](Arguments... args) { func(std::forward<Arguments>(args)...); POMDOG_ASSERT(conn); conn->Disconnect(); }); return *connection; }
int main(int argc, char* argv[]) { Classe myClass; Slot<int, float> slot; //declaring a slot that holds functions and functors which receive 2 parameters, an int and a float Signal<int, float> signal; //declares a signal compatible with the previous slot slot.Attach(&myClass, &Classe::miMethod); //adds to the slot a member method of myClass slot.Attach(&myFloat); //adds to the slot.Attach(&Classe::StaticMethod); //adds a static method to the slot signal.Connect(&slot); //connects the signal and the slot, so that firing the signal will also fire all the elements connected to the slot signal(2, 3); //fires the signal, which will fire the three elements connected to the slot slot.Detach(&myFloat); //detaches the function from the slot signal(2, 4); //now, firing the signal will only fire two elements of the slot slot.Detach(&myClass, &Classe::miMethod); //detaches the member of myClass signal(2, 5); //fires the only one element of the slot slot.Detach(&myClass, &Classe::miMethod2); //tryies to detach an element that is not present in the slot. Nothing happens signal(2, 6); slot.Detach(&Classe::StaticMethod); //detaches the last element of the signal signal(2, 7); //slot empty, nothing is fired //signal and slot for members with empty parameter list Signal<> empParamSignal; Slot<> empParamSlot; empParamSlot.Attach(&empty); empParamSignal.Connect(&empParamSlot); empParamSignal(); return 0; }
TEST(ConnectionList, ScopeGuardWithThreeConnections) { Signal<void(int)> valueChanged; std::vector<int> integers; { ConnectionList connections; auto slot = [&](int n){ integers.push_back(n); }; connections += valueChanged.Connect(slot); connections += valueChanged.Connect(slot); connections += valueChanged.Connect(slot); valueChanged(42); valueChanged(43); } valueChanged(44); ASSERT_EQ(6, integers.size()); EXPECT_EQ(42, integers[0]); EXPECT_EQ(42, integers[1]); EXPECT_EQ(42, integers[2]); EXPECT_EQ(43, integers[3]); EXPECT_EQ(43, integers[4]); EXPECT_EQ(43, integers[5]); }
void CInputManager::RegisterKeyBoardCallback( SKeyTriggerType type, const Function<void(void)>& function, bool exclusive) { WORD id = (WORD)((type.m_code << 8) + type.m_state); Signal<void(void)>* pSignal = NULL; TCallbackMap::iterator iter = m_callBacks.find(id); bool canAddNewSignal = iter == m_callBacks.end() || exclusive; BEATS_ASSERT(canAddNewSignal, _T("Can't register keybaord callback twice!")); if (iter != m_callBacks.end()) { m_stack[id].push_back(iter->second); } pSignal = new Signal<void(void)>(); m_callBacks[id] = pSignal; pSignal->Connect(function); }
TEST(ConnectionList, Disconnect) { Signal<void(std::string)> nameChanged; ConnectionList connections; std::string name; connections += nameChanged.Connect([&](std::string const& n) { name = n; }); nameChanged("alice"); EXPECT_EQ("alice", name); nameChanged("bob"); EXPECT_EQ("bob", name); nameChanged("chuck"); EXPECT_EQ("chuck", name); connections.Disconnect(); nameChanged("norris"); EXPECT_EQ("chuck", name); }