diff --git a/dlls/dinput/tests/force_feedback.c b/dlls/dinput/tests/force_feedback.c index 6903e490193..05b0ad9c427 100644 --- a/dlls/dinput/tests/force_feedback.c +++ b/dlls/dinput/tests/force_feedback.c @@ -5514,23 +5514,13 @@ static void test_windows_gaming_input(void) .report_id = 4, .report_len = 12, .report_buf = {4,0x01,0x00,0x70,0x17,0x7b,0x02,0xe9,0x04,0x4c,0x66,0x7f}, - .todo = TRUE, }, /* update effect */ - { - .code = IOCTL_HID_WRITE_REPORT, - .report_id = 3, - .report_len = 18, - .report_buf = {3,0x01,0x03,0x08,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xff,0xff,0x5a,0x00,0x00,0x00}, - .wine_only = TRUE, - .todo = TRUE, - }, { .code = IOCTL_HID_WRITE_REPORT, .report_id = 3, .report_len = 18, .report_buf = {3,0x01,0x03,0x08,0xff,0xff,0x00,0x00,0x00,0x00,0x00,0x00,0xff,0xff,0x99,0x00,0x00,0x00}, - .todo = TRUE, }, }; struct hid_expect expect_create_constant[] = @@ -6216,7 +6206,6 @@ static void test_windows_gaming_input(void) ok( hr == S_OK, "get_Kind returned %#lx\n", hr ); ok( condition_kind == ConditionForceEffectKind_Spring, "got kind %u\n", condition_kind ); hr = IConditionForceEffect_SetParameters( condition_effect, direction, 0.1, 0.2, 0.3, 0.4, 0.5, 0.6 ); - todo_wine ok( hr == S_OK, "SetParameters returned %#lx\n", hr ); IConditionForceEffect_Release( condition_effect ); diff --git a/dlls/windows.gaming.input/condition_effect.c b/dlls/windows.gaming.input/condition_effect.c index dccc50bb48f..c3a5a1fcd8b 100644 --- a/dlls/windows.gaming.input/condition_effect.c +++ b/dlls/windows.gaming.input/condition_effect.c @@ -110,10 +110,26 @@ static HRESULT WINAPI effect_get_Kind( IConditionForceEffect *iface, ConditionFo static HRESULT WINAPI effect_SetParameters( IConditionForceEffect *iface, Vector3 direction, FLOAT positive_coeff, FLOAT negative_coeff, FLOAT max_positive_magnitude, FLOAT max_negative_magnitude, FLOAT deadzone, FLOAT bias ) { - FIXME( "iface %p, direction %s, positive_coeff %f, negative_coeff %f, max_positive_magnitude %f, max_negative_magnitude %f, deadzone %f, bias %f stub!\n", + struct condition_effect *impl = impl_from_IConditionForceEffect( iface ); + WineForceFeedbackEffectParameters params = + { + .condition = + { + .type = WineForceFeedbackEffectType_Condition + impl->kind, + .direction = direction, + .positive_coeff = positive_coeff, + .negative_coeff = negative_coeff, + .max_positive_magnitude = max_positive_magnitude, + .max_negative_magnitude = max_negative_magnitude, + .deadzone = deadzone, + .bias = bias, + }, + }; + + TRACE( "iface %p, direction %s, positive_coeff %f, negative_coeff %f, max_positive_magnitude %f, max_negative_magnitude %f, deadzone %f, bias %f.\n", iface, debugstr_vector3( &direction ), positive_coeff, negative_coeff, max_positive_magnitude, max_negative_magnitude, deadzone, bias ); - return E_NOTIMPL; + return IWineForceFeedbackEffectImpl_put_Parameters( impl->IWineForceFeedbackEffectImpl_inner, params, NULL ); } static const struct IConditionForceEffectVtbl effect_vtbl = diff --git a/dlls/windows.gaming.input/force_feedback.c b/dlls/windows.gaming.input/force_feedback.c index 3e6b49ee1aa..dd10f86bd3e 100644 --- a/dlls/windows.gaming.input/force_feedback.c +++ b/dlls/windows.gaming.input/force_feedback.c @@ -162,7 +162,18 @@ static HRESULT WINAPI effect_impl_put_Parameters( IWineForceFeedbackEffectImpl * case WineForceFeedbackEffectType_Condition_Damper: case WineForceFeedbackEffectType_Condition_Inertia: case WineForceFeedbackEffectType_Condition_Friction: - FIXME("stub!\n"); + impl->repeat_count = 1; + impl->condition.lPositiveCoefficient = round( atan( params.condition.positive_coeff ) / M_PI_2 * 10000 ); + impl->condition.lNegativeCoefficient = round( atan( params.condition.negative_coeff ) / M_PI_2 * 10000 ); + impl->condition.dwPositiveSaturation = round( params.condition.max_positive_magnitude * 10000 ); + impl->condition.dwNegativeSaturation = round( params.condition.max_negative_magnitude * 10000 ); + impl->condition.lDeadBand = round( params.condition.deadzone * 10000 ); + impl->condition.lOffset = round( params.condition.bias * 10000 ); + impl->params.dwDuration = -1; + impl->params.dwStartDelay = 0; + impl->directions[0] = round( params.condition.direction.X * 10000 ); + impl->directions[1] = round( params.condition.direction.Y * 10000 ); + impl->directions[2] = round( params.condition.direction.Z * 10000 ); break; } diff --git a/dlls/windows.gaming.input/provider.idl b/dlls/windows.gaming.input/provider.idl index 4aacc43d80e..e7b6e96b8aa 100644 --- a/dlls/windows.gaming.input/provider.idl +++ b/dlls/windows.gaming.input/provider.idl @@ -37,6 +37,7 @@ namespace Windows.Gaming.Input.Custom { typedef enum WineForceFeedbackEffectType WineForceFeedbackEffectType; typedef struct WineGameControllerState WineGameControllerState; typedef struct WineGameControllerVibration WineGameControllerVibration; + typedef struct WineConditionEffectParameters WineConditionEffectParameters; typedef struct WineConstantEffectParameters WineConstantEffectParameters; typedef struct WineRampEffectParameters WineRampEffectParameters; typedef struct WinePeriodicEffectParameters WinePeriodicEffectParameters; @@ -92,6 +93,18 @@ namespace Windows.Gaming.Input.Custom { UINT16 right; }; + struct WineConditionEffectParameters + { + WineForceFeedbackEffectType type; + Windows.Foundation.Numerics.Vector3 direction; + FLOAT positive_coeff; + FLOAT negative_coeff; + FLOAT max_positive_magnitude; + FLOAT max_negative_magnitude; + FLOAT deadzone; + FLOAT bias; + }; + struct WineConstantEffectParameters { WineForceFeedbackEffectType type; @@ -137,6 +150,7 @@ namespace Windows.Gaming.Input.Custom { union WineForceFeedbackEffectParameters { WineForceFeedbackEffectType type; + WineConditionEffectParameters condition; WineConstantEffectParameters constant; WineRampEffectParameters ramp; WinePeriodicEffectParameters periodic;