Commit 33dc3db0 authored by Rémi Bernon's avatar Rémi Bernon Committed by Alexandre Julliard

dinput: Implement HID joystick IDirectInputEffect_(Start|Stop).

parent 4315d279
...@@ -145,6 +145,7 @@ struct hid_joystick_effect ...@@ -145,6 +145,7 @@ struct hid_joystick_effect
IDirectInputEffect IDirectInputEffect_iface; IDirectInputEffect IDirectInputEffect_iface;
LONG ref; LONG ref;
USAGE type; USAGE type;
ULONG index;
struct list entry; struct list entry;
struct hid_joystick *joystick; struct hid_joystick *joystick;
...@@ -2134,14 +2135,97 @@ static HRESULT WINAPI hid_joystick_effect_SetParameters( IDirectInputEffect *ifa ...@@ -2134,14 +2135,97 @@ static HRESULT WINAPI hid_joystick_effect_SetParameters( IDirectInputEffect *ifa
static HRESULT WINAPI hid_joystick_effect_Start( IDirectInputEffect *iface, DWORD iterations, DWORD flags ) static HRESULT WINAPI hid_joystick_effect_Start( IDirectInputEffect *iface, DWORD iterations, DWORD flags )
{ {
FIXME( "iface %p, iterations %u, flags %#x stub!\n", iface, iterations, flags ); struct hid_joystick_effect *impl = impl_from_IDirectInputEffect( iface );
return DIERR_UNSUPPORTED; struct pid_control_report *effect_control = &impl->joystick->pid_effect_control;
ULONG count, report_len = impl->joystick->caps.OutputReportByteLength;
PHIDP_PREPARSED_DATA preparsed = impl->joystick->preparsed;
HANDLE device = impl->joystick->device;
NTSTATUS status;
USAGE control;
HRESULT hr;
TRACE( "iface %p, iterations %u, flags %#x.\n", iface, iterations, flags );
if ((flags & ~(DIES_NODOWNLOAD|DIES_SOLO))) return DIERR_INVALIDPARAM;
if (flags & DIES_SOLO) control = PID_USAGE_OP_EFFECT_START_SOLO;
else control = PID_USAGE_OP_EFFECT_START;
EnterCriticalSection( &impl->joystick->base.crit );
if (!impl->joystick->base.acquired || !(impl->joystick->base.dwCoopLevel & DISCL_EXCLUSIVE))
hr = DIERR_NOTEXCLUSIVEACQUIRED;
else if ((flags & DIES_NODOWNLOAD) && !impl->index)
hr = DIERR_NOTDOWNLOADED;
else if ((flags & DIES_NODOWNLOAD) || !FAILED(hr = IDirectInputEffect_Download( iface )))
{
count = 1;
status = HidP_InitializeReportForID( HidP_Output, effect_control->id, preparsed,
impl->effect_control_buf, report_len );
if (status != HIDP_STATUS_SUCCESS) hr = status;
else status = HidP_SetUsageValue( HidP_Output, HID_USAGE_PAGE_PID, 0, PID_USAGE_EFFECT_BLOCK_INDEX,
impl->index, preparsed, impl->effect_control_buf, report_len );
if (status != HIDP_STATUS_SUCCESS) hr = status;
else status = HidP_SetUsages( HidP_Output, HID_USAGE_PAGE_PID, effect_control->control_coll,
&control, &count, preparsed, impl->effect_control_buf, report_len );
if (status != HIDP_STATUS_SUCCESS) hr = status;
else status = HidP_SetUsageValue( HidP_Output, HID_USAGE_PAGE_PID, 0, PID_USAGE_LOOP_COUNT,
iterations, preparsed, impl->effect_control_buf, report_len );
if (status != HIDP_STATUS_SUCCESS) hr = status;
else if (WriteFile( device, impl->effect_control_buf, report_len, NULL, NULL )) hr = DI_OK;
else hr = DIERR_INPUTLOST;
}
LeaveCriticalSection( &impl->joystick->base.crit );
return hr;
} }
static HRESULT WINAPI hid_joystick_effect_Stop( IDirectInputEffect *iface ) static HRESULT WINAPI hid_joystick_effect_Stop( IDirectInputEffect *iface )
{ {
FIXME( "iface %p stub!\n", iface ); struct hid_joystick_effect *impl = impl_from_IDirectInputEffect( iface );
return DIERR_UNSUPPORTED; struct pid_control_report *effect_control = &impl->joystick->pid_effect_control;
ULONG count, report_len = impl->joystick->caps.OutputReportByteLength;
PHIDP_PREPARSED_DATA preparsed = impl->joystick->preparsed;
HANDLE device = impl->joystick->device;
NTSTATUS status;
USAGE control;
HRESULT hr;
TRACE( "iface %p.\n", iface );
EnterCriticalSection( &impl->joystick->base.crit );
if (!impl->joystick->base.acquired || !(impl->joystick->base.dwCoopLevel & DISCL_EXCLUSIVE))
hr = DIERR_NOTEXCLUSIVEACQUIRED;
else if (!impl->index)
hr = DIERR_NOTDOWNLOADED;
else
{
count = 1;
control = PID_USAGE_OP_EFFECT_STOP;
status = HidP_InitializeReportForID( HidP_Output, effect_control->id, preparsed,
impl->effect_control_buf, report_len );
if (status != HIDP_STATUS_SUCCESS) hr = status;
else status = HidP_SetUsageValue( HidP_Output, HID_USAGE_PAGE_PID, 0, PID_USAGE_EFFECT_BLOCK_INDEX,
impl->index, preparsed, impl->effect_control_buf, report_len );
if (status != HIDP_STATUS_SUCCESS) hr = status;
else status = HidP_SetUsages( HidP_Output, HID_USAGE_PAGE_PID, effect_control->control_coll,
&control, &count, preparsed, impl->effect_control_buf, report_len );
if (status != HIDP_STATUS_SUCCESS) hr = status;
else status = HidP_SetUsageValue( HidP_Output, HID_USAGE_PAGE_PID, 0, PID_USAGE_LOOP_COUNT,
0, preparsed, impl->effect_control_buf, report_len );
if (status != HIDP_STATUS_SUCCESS) hr = status;
else if (WriteFile( device, impl->effect_control_buf, report_len, NULL, NULL )) hr = DI_OK;
else hr = DIERR_INPUTLOST;
}
LeaveCriticalSection( &impl->joystick->base.crit );
return hr;
} }
static HRESULT WINAPI hid_joystick_effect_GetEffectStatus( IDirectInputEffect *iface, DWORD *status ) static HRESULT WINAPI hid_joystick_effect_GetEffectStatus( IDirectInputEffect *iface, DWORD *status )
......
...@@ -5765,10 +5765,8 @@ static void test_periodic_effect( IDirectInputDevice8W *device, HANDLE file ) ...@@ -5765,10 +5765,8 @@ static void test_periodic_effect( IDirectInputDevice8W *device, HANDLE file )
check_member( periodic, expect_periodic, "%u", dwPeriod ); check_member( periodic, expect_periodic, "%u", dwPeriod );
hr = IDirectInputEffect_Start( effect, 1, DIES_NODOWNLOAD ); hr = IDirectInputEffect_Start( effect, 1, DIES_NODOWNLOAD );
todo_wine
ok( hr == DIERR_NOTDOWNLOADED, "Start returned %#x\n", hr ); ok( hr == DIERR_NOTDOWNLOADED, "Start returned %#x\n", hr );
hr = IDirectInputEffect_Stop( effect ); hr = IDirectInputEffect_Stop( effect );
todo_wine
ok( hr == DIERR_NOTDOWNLOADED, "Stop returned %#x\n", hr ); ok( hr == DIERR_NOTDOWNLOADED, "Stop returned %#x\n", hr );
set_hid_expect( file, expect_download, 3 * sizeof(struct hid_expect) ); set_hid_expect( file, expect_download, 3 * sizeof(struct hid_expect) );
...@@ -5782,7 +5780,6 @@ static void test_periodic_effect( IDirectInputDevice8W *device, HANDLE file ) ...@@ -5782,7 +5780,6 @@ static void test_periodic_effect( IDirectInputDevice8W *device, HANDLE file )
ok( hr == DI_NOEFFECT, "Download returned %#x\n", hr ); ok( hr == DI_NOEFFECT, "Download returned %#x\n", hr );
hr = IDirectInputEffect_Start( effect, 1, 0xdeadbeef ); hr = IDirectInputEffect_Start( effect, 1, 0xdeadbeef );
todo_wine
ok( hr == DIERR_INVALIDPARAM, "Start returned %#x\n", hr ); ok( hr == DIERR_INVALIDPARAM, "Start returned %#x\n", hr );
set_hid_expect( file, &expect_start_solo, sizeof(expect_start_solo) ); set_hid_expect( file, &expect_start_solo, sizeof(expect_start_solo) );
...@@ -5845,10 +5842,8 @@ static void test_periodic_effect( IDirectInputDevice8W *device, HANDLE file ) ...@@ -5845,10 +5842,8 @@ static void test_periodic_effect( IDirectInputDevice8W *device, HANDLE file )
set_hid_expect( file, NULL, 0 ); set_hid_expect( file, NULL, 0 );
hr = IDirectInputEffect_Start( effect, 1, DIES_NODOWNLOAD ); hr = IDirectInputEffect_Start( effect, 1, DIES_NODOWNLOAD );
todo_wine
ok( hr == DIERR_NOTEXCLUSIVEACQUIRED, "Start returned %#x\n", hr ); ok( hr == DIERR_NOTEXCLUSIVEACQUIRED, "Start returned %#x\n", hr );
hr = IDirectInputEffect_Stop( effect ); hr = IDirectInputEffect_Stop( effect );
todo_wine
ok( hr == DIERR_NOTEXCLUSIVEACQUIRED, "Stop returned %#x\n", hr ); ok( hr == DIERR_NOTEXCLUSIVEACQUIRED, "Stop returned %#x\n", hr );
set_hid_expect( file, &expect_dc_reset, sizeof(expect_dc_reset) ); set_hid_expect( file, &expect_dc_reset, sizeof(expect_dc_reset) );
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment