dinput: Clear action mapping with SetDataFormat().

Signed-off-by: Arkadiusz Hiler <ahiler@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Arkadiusz Hiler 2021-03-08 14:36:09 +02:00 committed by Alexandre Julliard
parent d3e7e0426c
commit 542f613456
2 changed files with 24 additions and 6 deletions

View file

@ -833,6 +833,7 @@ HRESULT _set_action_map(LPDIRECTINPUTDEVICE8W iface, LPDIACTIONFORMATW lpdiaf, L
DWORD username_size = MAX_PATH;
int i, action = 0, num_actions = 0;
unsigned int offset = 0;
ActionMap *action_map;
if (This->acquired) return DIERR_ACQUIRED;
@ -848,15 +849,12 @@ HRESULT _set_action_map(LPDIRECTINPUTDEVICE8W iface, LPDIACTIONFORMATW lpdiaf, L
if (num_actions == 0) return DI_NOEFFECT;
This->num_actions = num_actions;
/* Construct the dataformat and actionmap */
obj_df = HeapAlloc(GetProcessHeap(), 0, sizeof(DIOBJECTDATAFORMAT)*num_actions);
data_format.rgodf = (LPDIOBJECTDATAFORMAT)obj_df;
data_format.dwNumObjs = num_actions;
HeapFree(GetProcessHeap(), 0, This->action_map);
This->action_map = HeapAlloc(GetProcessHeap(), 0, sizeof(ActionMap)*num_actions);
action_map = HeapAlloc(GetProcessHeap(), 0, sizeof(ActionMap)*num_actions);
for (i = 0; i < lpdiaf->dwNumActions; i++)
{
@ -873,8 +871,8 @@ HRESULT _set_action_map(LPDIRECTINPUTDEVICE8W iface, LPDIACTIONFORMATW lpdiaf, L
memcpy(&obj_df[action], obj, df->dwObjSize);
This->action_map[action].uAppData = lpdiaf->rgoAction[i].uAppData;
This->action_map[action].offset = offset;
action_map[action].uAppData = lpdiaf->rgoAction[i].uAppData;
action_map[action].offset = offset;
obj_df[action].dwOfs = offset;
offset += (type & DIDFT_BUTTON) ? 1 : 4;
@ -884,6 +882,9 @@ HRESULT _set_action_map(LPDIRECTINPUTDEVICE8W iface, LPDIACTIONFORMATW lpdiaf, L
IDirectInputDevice8_SetDataFormat(iface, &data_format);
This->action_map = action_map;
This->num_actions = num_actions;
HeapFree(GetProcessHeap(), 0, obj_df);
/* Set the device properties according to the action format */
@ -962,6 +963,7 @@ void queue_event(LPDIRECTINPUTDEVICE8A iface, int inst_id, DWORD data, DWORD tim
This->data_queue[This->queue_head].dwData = data;
This->data_queue[This->queue_head].dwTimeStamp = time;
This->data_queue[This->queue_head].dwSequence = seq;
This->data_queue[This->queue_head].uAppData = -1;
/* Set uAppData by means of action mapping */
if (This->num_actions > 0)
@ -1063,6 +1065,10 @@ HRESULT WINAPI IDirectInputDevice2WImpl_SetDataFormat(LPDIRECTINPUTDEVICE8W ifac
EnterCriticalSection(&This->crit);
HeapFree(GetProcessHeap(), 0, This->action_map);
This->action_map = NULL;
This->num_actions = 0;
release_DataFormat(&This->data_format);
res = create_DataFormat(df, &This->data_format);

View file

@ -362,6 +362,18 @@ static void test_action_mapping(void)
/* Test keyboard input */
test_device_input(data.keyboard, INPUT_KEYBOARD, VK_SPACE, 2);
/* setting format should reset action map */
hr = IDirectInputDevice8_SetDataFormat(data.keyboard, &c_dfDIKeyboard);
ok (SUCCEEDED(hr), "IDirectInputDevice8_SetDataFormat failed: %08x\n", hr);
test_device_input(data.keyboard, INPUT_KEYBOARD, VK_SPACE, -1);
/* back to action map */
hr = IDirectInputDevice8_SetActionMap(data.keyboard, data.lpdiaf, NULL, 0);
ok (SUCCEEDED(hr), "SetActionMap should succeed hr=%08x\n", hr);
test_device_input(data.keyboard, INPUT_KEYBOARD, VK_SPACE, 2);
/* Test BuildActionMap with no suitable actions for a device */
IDirectInputDevice_Unacquire(data.keyboard);
af.dwDataSize = 4 * DITEST_KEYBOARDSPACE;