Implemented support for Thrustmaster Dual Power 3 gamepad vsb

This commit is contained in:
Ingo Ruhnke 2009-06-19 04:38:09 +02:00
parent 080541f30e
commit 2571ada962
10 changed files with 77 additions and 21 deletions

3
NEWS
View file

@ -3,6 +3,7 @@ xboxdrv 0.4.7 - (??/May/2009)
* support for Pelican TSZ360 pad
* support for Saitek P3200 pad
* support for Thrustmaster Firestorm Dual Power (044f:b312)
* deadzone support for trigger via --deadzone-trigger NUM
* some documentation improvements
@ -41,7 +42,7 @@ xboxdrv 0.4.3 - (17/Jan/2009)
* added support for X11 keysym in --ui-buttonmap
* added --ui-clear and 'void' mappings to unmap buttons and axis
* fixed LED handling for wireless gamepads
* Thrustmaster Firestorm Dual Power support
* Thrustmaster Firestorm Dual Power support (044f:b304)
* added --name option to set device name
* added JS_${NUM} name to address joystick buttons by number instead
of name

View file

@ -209,6 +209,10 @@ CommandLineOptions::parse_args(int argc, char** argv)
{
opts.gamepad_type = GAMEPAD_FIRESTORM;
}
else if (strcmp(argv[i], "firestorm-vsb") == 0)
{
opts.gamepad_type = GAMEPAD_FIRESTORM_VSB;
}
else
{
RAISE_EXCEPTION("unknown type: " << argv[i] << '\n'
@ -218,7 +222,8 @@ CommandLineOptions::parse_args(int argc, char** argv)
<< " * xbox360\n"
<< " * xbox360-guitar\n"
<< " * xbox360-wireless\n"
<< " * firestorm\n");
<< " * firestorm\n"
<< " * firestorm-vsb\n");
}
}
else

View file

@ -50,7 +50,7 @@ struct Firestorm_vsb_Msg
int y1 :8;
int x2 :8;
unsigned int y2 :8;
};
} __attribute__((__packed__));
// 044f:b304
struct FirestormMsg
@ -81,8 +81,9 @@ struct FirestormMsg
unsigned int y2 :8;
} __attribute__((__packed__));
FirestormDualController::FirestormDualController(struct usb_device* dev)
: left_rumble(-1),
FirestormDualController::FirestormDualController(struct usb_device* dev, bool is_vsb_)
: is_vsb(is_vsb_),
left_rumble(-1),
right_rumble(-1)
{
handle = usb_open(dev);
@ -114,6 +115,29 @@ FirestormDualController::~FirestormDualController()
void
FirestormDualController::set_rumble(uint8_t left, uint8_t right)
{
if (is_vsb)
set_rumble_vsb(left, right);
else
set_rumble_default(left, right);
}
void
FirestormDualController::set_rumble_vsb(uint8_t left, uint8_t right)
{
if (left_rumble != left ||
right_rumble != right)
{
left_rumble = left;
right_rumble = right;
char cmd[] = { left, right, 0x00, 0x00 };
usb_control_msg(handle, 0x21, 0x09, 0x0200, 0x00, cmd, sizeof(cmd), 0);
}
}
void
FirestormDualController::set_rumble_default(uint8_t left, uint8_t right)
{
if (left_rumble != left ||
right_rumble != right)
@ -152,8 +176,10 @@ inline int16_t scale_8to16(int8_t a)
bool
FirestormDualController::read(XboxGenericMsg& msg, bool verbose, int timeout)
{
//return read_vsb(msg, verbose, timeout);
return read_default(msg, verbose, timeout);
if (is_vsb)
return read_vsb(msg, verbose, timeout);
else
return read_default(msg, verbose, timeout);
}
bool

View file

@ -26,6 +26,7 @@
class FirestormDualController : public XboxGenericController
{
private:
bool is_vsb;
struct usb_device* dev;
struct usb_dev_handle* handle;
@ -33,10 +34,12 @@ private:
int right_rumble;
public:
FirestormDualController(struct usb_device* dev);
FirestormDualController(struct usb_device* dev, bool is_vsb);
~FirestormDualController();
void set_rumble(uint8_t left, uint8_t right);
void set_rumble_default(uint8_t left, uint8_t right);
void set_rumble_vsb(uint8_t left, uint8_t right);
void set_led(uint8_t status);
/** @param timeout timeout in msec, 0 means forever */

View file

@ -355,6 +355,7 @@ uInput::uInput(const XPadDevice& dev, uInputCfg config_)
case GAMEPAD_XBOX:
case GAMEPAD_XBOX360_WIRELESS:
case GAMEPAD_FIRESTORM:
case GAMEPAD_FIRESTORM_VSB:
setup_xbox360_gamepad(dev.type);
break;

View file

@ -256,6 +256,19 @@ Xboxdrv::find_xbox360_controller(int id, struct usb_device** xbox_device, XPadDe
return 0;
}
void
Xboxdrv::apply_modifier(XboxGenericMsg& msg, int msec_delta, const CommandLineOptions& opts) const
{
apply_calibration_map(msg, opts.calibration_map);
// Apply modifier
apply_deadzone(msg, opts);
if (opts.square_axis)
apply_square_axis(msg);
}
void
Xboxdrv::controller_loop(GamepadType type, uInput* uinput, XboxGenericController* controller, const CommandLineOptions& opts)
{
@ -278,7 +291,7 @@ Xboxdrv::controller_loop(GamepadType type, uInput* uinput, XboxGenericController
// opts.uinput_config.force_feedback)
timeout = 25; // FIXME: How long should we wait for a new event?
memset(&oldmsg, 0, sizeof(oldmsg));
memset(&oldmsg, 0, sizeof(oldmsg));
memset(&oldrealmsg, 0, sizeof(oldrealmsg));
uint32_t last_time = get_time();
@ -301,13 +314,7 @@ Xboxdrv::controller_loop(GamepadType type, uInput* uinput, XboxGenericController
int msec_delta = this_time - last_time;
last_time = this_time;
apply_calibration_map(msg, opts.calibration_map);
// Apply modifier
apply_deadzone(msg, opts);
if (opts.square_axis)
apply_square_axis(msg);
apply_modifier(msg, msec_delta, opts);
if (autofire_modifier.get())
autofire_modifier->update(msec_delta, msg);
@ -321,7 +328,7 @@ Xboxdrv::controller_loop(GamepadType type, uInput* uinput, XboxGenericController
if (!opts.axis_map.empty())
apply_axis_map(msg, opts.axis_map);
if (memcmp(&msg, &oldmsg, sizeof(XboxGenericMsg)))
if (memcmp(&msg, &oldmsg, sizeof(XboxGenericMsg)) != 0)
{ // Only send a new event out if something has changed,
// this is useful since some controllers send events
// even if nothing has changed, deadzone can cause this
@ -345,7 +352,8 @@ Xboxdrv::controller_loop(GamepadType type, uInput* uinput, XboxGenericController
{
set_rumble(controller, opts.rumble_gain, msg.xbox360.lt, msg.xbox360.rt);
}
else if (type == GAMEPAD_FIRESTORM)
else if (type == GAMEPAD_FIRESTORM ||
type == GAMEPAD_FIRESTORM_VSB)
{
set_rumble(controller, opts.rumble_gain,
std::min(255, abs((msg.xbox360.y1>>8)*2)),
@ -472,7 +480,11 @@ Xboxdrv::run_main(const CommandLineOptions& opts)
break;
case GAMEPAD_FIRESTORM:
controller = std::auto_ptr<XboxGenericController>(new FirestormDualController(dev));
controller = std::auto_ptr<XboxGenericController>(new FirestormDualController(dev, false));
break;
case GAMEPAD_FIRESTORM_VSB:
controller = std::auto_ptr<XboxGenericController>(new FirestormDualController(dev, true));
break;
default:

View file

@ -40,6 +40,7 @@ private:
void controller_loop(GamepadType type, uInput* uinput,
XboxGenericController* controller,
const CommandLineOptions& opts);
void apply_modifier(XboxGenericMsg& msg, int msec_delta, const CommandLineOptions& opts) const;
bool find_controller_by_path(const char* busid, const char* devid,struct usb_device** xbox_device) const;
void find_controller(struct usb_device*& dev,

View file

@ -45,6 +45,9 @@ std::string gamepadtype_to_string(const GamepadType& type)
case GAMEPAD_FIRESTORM:
return "firestorm";
case GAMEPAD_FIRESTORM_VSB:
return "firestorm-vsb";
default:
assert(!"Unknown gamepad type supplied");
}
@ -72,6 +75,9 @@ std::ostream& operator<<(std::ostream& out, const GamepadType& type)
case GAMEPAD_FIRESTORM:
return out << "Firestorm Dual Power";
case GAMEPAD_FIRESTORM_VSB:
return out << "Firestorm Dual Power (vsb)";
default:
return out << "unknown" << std::endl;
}

View file

@ -28,7 +28,8 @@ enum GamepadType {
GAMEPAD_XBOX360,
GAMEPAD_XBOX360_WIRELESS,
GAMEPAD_XBOX360_GUITAR,
GAMEPAD_FIRESTORM
GAMEPAD_FIRESTORM,
GAMEPAD_FIRESTORM_VSB
};
enum XboxMsgType {

View file

@ -80,7 +80,7 @@ XPadDevice xpad_devices[] = {
{ GAMEPAD_XBOX360, 0x12ab, 0x0004, "DDR Universe 2 Mat" },
{ GAMEPAD_FIRESTORM, 0x044f, 0xb304, "ThrustMaster, Inc. Firestorm Dual Power" },
//{ GAMEPAD_FIRESTORM, 0x044f, 0xb312, "ThrustMaster, Inc. Firestorm Dual Power (vs b)" },
{ GAMEPAD_FIRESTORM_VSB, 0x044f, 0xb312, "ThrustMaster, Inc. Firestorm Dual Power (vs b)" },
};
const int xpad_devices_count = sizeof(xpad_devices)/sizeof(XPadDevice);