#include "unittest/TestSuite.h" #include "inputcontroller/InputPlayback.h" #include "utilities/IOUtilities.h" #include "utilities/printfFormats.h" static void verifyInit(InputPlayback * playback, InputController * controller, InputSession * session, unsigned int lineNumber) { TestCase_assert(playback != NULL, "Expected non-NULL but got NULL (%u)", lineNumber); TestCase_assert(playback->inputController == controller, "Expected %p but got %p (%u)", controller, playback->inputController, lineNumber); TestCase_assert(playback->inputSession == session, "Expected %p but got %p (%u)", session, playback->inputSession, lineNumber); TestCase_assert(playback->eventDispatcher != NULL, "Expected non-NULL but got NULL (%u)", lineNumber); TestCase_assert(playback->frameIndex == 0, "Expected 0 but got %u (%u)", playback->frameIndex, lineNumber); TestCase_assert(playback->vtable == &InputPlayback_class, "Expected %p but got %p (%u)", &InputPlayback_class, playback->vtable, lineNumber); } static void testInit() { InputPlayback playback, * playbackPtr; InputController * controller = (InputController *) 1; InputSession * session = InputSession_loadData("\x01\x00\x00\x00\x00\x00\x00\x00", 8, NULL); memset(&playback, 0x00, sizeof(playback)); stemobject_assign_vtable(playback, InputPlayback); InputPlayback_init(&playback, NULL, NULL); verifyInit(&playback, NULL, NULL, __LINE__); InputPlayback_dispose(&playback); memset(&playback, 0xFF, sizeof(playback)); stemobject_assign_vtable(playback, InputPlayback); InputPlayback_init(&playback, controller, session); verifyInit(&playback, controller, session, __LINE__); InputPlayback_dispose(&playback); playbackPtr = InputPlayback_create(controller, session); verifyInit(playbackPtr, controller, session, __LINE__); InputPlayback_dispose(playbackPtr); InputSession_dispose(session); } static unsigned int actionDownCalls, actionUpCalls, actionRepeatCalls, motionCalls; static Atom lastDownActionID, lastUpActionID, lastRepeatActionID, lastMotionActionID; static double lastDownTimestamp, lastUpTimestamp, lastRepeatTimestamp, lastMotionTimestamp; static enum InputSessionEventType lastCallType; static fixed16_16 lastMotionValueX, lastMotionValueY, lastMotionRawValueX, lastMotionRawValueY; static bool actionDownCallback(Atom eventID, void * eventData, void * context) { struct InputController_event * event = eventData; actionDownCalls++; lastDownActionID = event->actionID; lastDownTimestamp = event->timestamp; lastCallType = INPUT_SESSION_EVENT_ACTION_DOWN; return true; } static bool actionUpCallback(Atom eventID, void * eventData, void * context) { struct InputController_event * event = eventData; actionUpCalls++; lastUpActionID = event->actionID; lastUpTimestamp = event->timestamp; lastCallType = INPUT_SESSION_EVENT_ACTION_UP; return true; } static bool actionRepeatCallback(Atom eventID, void * eventData, void * context) { struct InputController_event * event = eventData; actionRepeatCalls++; lastRepeatActionID = event->actionID; lastRepeatTimestamp = event->timestamp; lastCallType = INPUT_SESSION_EVENT_ACTION_REPEAT; return true; } static bool motionCallback(Atom eventID, void * eventData, void * context) { struct InputController_motionEvent * event = eventData; motionCalls++; lastMotionActionID = event->actionID; lastMotionTimestamp = event->timestamp; lastMotionValueX = event->valueX; lastMotionValueY = event->valueY; lastMotionRawValueX = event->rawValueX; lastMotionRawValueY = event->rawValueY; return true; } static void testBasicPlayback() { InputSession * session; InputPlayback * playback; InputController testInputController; char testData1[] = "\x01\x00" "\x00\x00\x00\x00" "\x01\x00" "\x61\x00" "\x00\x00\x00\x00\x00\x00\x00" "\x00\x00\x00\x00\x00\x00\x01"; char testData2[] = "\x01\x00" "\x00\x00\x00\x00" "\x02\x00" "\x61\x00" "\x62\x00" "\x00\x00\x00\x00\x01\x00\x00" "\x01\x00\x00\x00\x00\x00\x00" "\x02\x00\x00\x00\x01\x00\x01" "\x01\x00\x00\x00\x00\x00\x02\x00\x00\x01\x00\x00\x00\x02\x00\x00\x00\x03\x00\x00\x00\x04\x00"; stemobject_assign_vtable(testInputController, InputController); InputController_init(&testInputController, NULL, NULL, NULL); EventDispatcher_registerForEvent(testInputController.eventDispatcher, ATOM(INPUT_CONTROLLER_EVENT_ACTION_DOWN), actionDownCallback, NULL); EventDispatcher_registerForEvent(testInputController.eventDispatcher, ATOM(INPUT_CONTROLLER_EVENT_ACTION_UP), actionUpCallback, NULL); EventDispatcher_registerForEvent(testInputController.eventDispatcher, ATOM(INPUT_CONTROLLER_EVENT_ACTION_REPEAT), actionRepeatCallback, NULL); EventDispatcher_registerForEvent(testInputController.eventDispatcher, ATOM(INPUT_CONTROLLER_EVENT_MOTION), motionCallback, NULL); session = InputSession_loadData(testData1, sizeof(testData1) - 1, NULL); playback = InputPlayback_create((InputController *) &testInputController, session); actionDownCalls = actionUpCalls = actionRepeatCalls = motionCalls = 0; InputPlayback_step(playback, 1.0); TestCase_assertUIntEqual(actionDownCalls, 1); TestCase_assertStringPointerEqual(lastDownActionID, ATOM("a")); TestCase_assertDoubleEqual(lastDownTimestamp, 1.0); TestCase_assertUIntEqual(actionUpCalls, 1); TestCase_assertStringPointerEqual(lastUpActionID, ATOM("a")); TestCase_assertDoubleEqual(lastUpTimestamp, 1.0); TestCase_assertIntEqual(lastCallType, INPUT_SESSION_EVENT_ACTION_UP); InputPlayback_dispose(playback); InputSession_dispose(session); session = InputSession_loadData(testData2, sizeof(testData2) - 1, NULL); playback = InputPlayback_create(&testInputController, session); actionDownCalls = actionUpCalls = actionRepeatCalls = motionCalls = 0; InputPlayback_step(playback, 2.0); TestCase_assertUIntEqual(actionDownCalls, 1); TestCase_assertStringPointerEqual(lastDownActionID, ATOM("b")); TestCase_assertDoubleEqual(lastDownTimestamp, 2.0); InputPlayback_step(playback, 3.0); TestCase_assertUIntEqual(actionDownCalls, 2); TestCase_assertStringPointerEqual(lastDownActionID, ATOM("a")); TestCase_assertDoubleEqual(lastDownTimestamp, 3.0); InputPlayback_step(playback, 4.0); TestCase_assertUIntEqual(actionDownCalls, 2); TestCase_assertUIntEqual(actionUpCalls, 0); InputPlayback_step(playback, 5.0); TestCase_assertUIntEqual(actionUpCalls, 1); TestCase_assertStringPointerEqual(lastUpActionID, ATOM("b")); TestCase_assertDoubleEqual(lastUpTimestamp, 5.0); InputPlayback_step(playback, 6.0); TestCase_assertUIntEqual(motionCalls, 1); TestCase_assertStringPointerEqual(lastMotionActionID, ATOM("a")); TestCase_assertDoubleEqual(lastMotionTimestamp, 6.0); TestCase_assertFixed16_16Equal(lastMotionValueX, 0x10000); TestCase_assertFixed16_16Equal(lastMotionValueY, 0x20000); TestCase_assertFixed16_16Equal(lastMotionRawValueX, 0x30000); TestCase_assertFixed16_16Equal(lastMotionRawValueY, 0x40000); InputPlayback_dispose(playback); InputSession_dispose(session); } static unsigned int playbackCompleteCalls; bool playbackComplete(Atom eventID, void * eventData, void * context) { playbackCompleteCalls++; return true; } static void testPlaybackCompleteEvent() { InputSession * session; InputPlayback * playback; InputController testInputController; char testData1[] = "\x01\x00" "\x00\x00\x00\x00" "\x01\x00" "\x61\x00" "\x01\x00\x00\x00\x00\x00\x00"; stemobject_assign_vtable(testInputController, InputController); InputController_init(&testInputController, NULL, NULL, NULL); playbackCompleteCalls = 0; session = InputSession_loadData(testData1, sizeof(testData1) - 1, NULL); playback = InputPlayback_create(&testInputController, session); EventDispatcher_registerForEvent(playback->eventDispatcher, ATOM(INPUT_PLAYBACK_EVENT_PLAYBACK_COMPLETE), playbackComplete, NULL); InputPlayback_step(playback, 1.0); TestCase_assertUIntEqual(playbackCompleteCalls, 0); InputPlayback_step(playback, 2.0); TestCase_assertUIntEqual(playbackCompleteCalls, 1); InputPlayback_step(playback, 3.0); TestCase_assertUIntEqual(playbackCompleteCalls, 1); InputPlayback_dispose(playback); InputSession_dispose(session); } static void testRewind() { InputSession * session; InputPlayback * playback; InputController testInputController; char testData1[] = "\x01\x00" "\x00\x00\x00\x00" "\x01\x00" "\x61\x00" "\x00\x00\x00\x00\x00\x00\x00" "\x00\x00\x00\x00\x00\x00\x01"; stemobject_assign_vtable(testInputController, InputController); InputController_init(&testInputController, NULL, NULL, NULL); EventDispatcher_registerForEvent(testInputController.eventDispatcher, ATOM(INPUT_CONTROLLER_EVENT_ACTION_DOWN), actionDownCallback, NULL); EventDispatcher_registerForEvent(testInputController.eventDispatcher, ATOM(INPUT_CONTROLLER_EVENT_ACTION_UP), actionUpCallback, NULL); EventDispatcher_registerForEvent(testInputController.eventDispatcher, ATOM(INPUT_CONTROLLER_EVENT_ACTION_REPEAT), actionRepeatCallback, NULL); EventDispatcher_registerForEvent(testInputController.eventDispatcher, ATOM(INPUT_CONTROLLER_EVENT_MOTION), motionCallback, NULL); session = InputSession_loadData(testData1, sizeof(testData1) - 1, NULL); playback = InputPlayback_create(&testInputController, session); actionDownCalls = actionUpCalls = 0; InputPlayback_step(playback, 1.0); TestCase_assertUIntEqual(actionDownCalls, 1); TestCase_assertStringPointerEqual(lastDownActionID, ATOM("a")); TestCase_assertDoubleEqual(lastDownTimestamp, 1.0); TestCase_assertUIntEqual(actionUpCalls, 1); TestCase_assertStringPointerEqual(lastUpActionID, ATOM("a")); TestCase_assertDoubleEqual(lastUpTimestamp, 1.0); TestCase_assertIntEqual(lastCallType, INPUT_SESSION_EVENT_ACTION_UP); InputPlayback_rewind(playback); InputPlayback_step(playback, 2.0); TestCase_assertUIntEqual(actionDownCalls, 2); TestCase_assertStringPointerEqual(lastDownActionID, ATOM("a")); TestCase_assertDoubleEqual(lastDownTimestamp, 2.0); TestCase_assertUIntEqual(actionUpCalls, 2); TestCase_assertStringPointerEqual(lastUpActionID, ATOM("a")); TestCase_assertDoubleEqual(lastUpTimestamp, 2.0); TestCase_assertIntEqual(lastCallType, INPUT_SESSION_EVENT_ACTION_UP); InputPlayback_dispose(playback); InputSession_dispose(session); } TEST_SUITE(InputPlaybackTest, testInit, testBasicPlayback, testPlaybackCompleteEvent, testRewind)