通过套接字将Xinput状态发送到另一个Controller并将其传递给程序

时间:2018-01-17 23:55:25

标签: c++ controller xinput

所以事实上,我真的很喜欢和朋友一起玩DS3游戏,每当有人去世,控制器就会传递给下一个典型的沙发游戏。但通常我们没有时间互相访问,所以唯一的选择就是在线MP。由于我不喜欢这样,我的朋友大多没有DS3我想用XInput创建一个程序,它不断获取控制器状态并通过WinSockets将其镜像到另一个,所以我的朋友可以通过他们的控制器来控制我的游戏。我已经为一个带有一些基本功能的控制器类编写了一些快速代码,以便更好地了解XInput。现在我的问题是:DS3使用XInput还是DInput?无论哪种方式,我如何让DS3解释我的输入?我希望这个问题足够具体。

如果到目前为止我的代码是必要的:

CPad.h:

#pragma once

#include <iostream>
#include <Windows.h>
#include <Xinput.h>
#include <limits.h>
#include <time.h>

using namespace std;

class Ctimer
{
private:
    clock_t cur_time;
    clock_t last_time;

public:
    Ctimer() {
        cur_time = last_time = clock();
    }
    void update() {
        cur_time = clock();
    }
    void reset() {
        last_time = cur_time;
    }
    clock_t GetElapsed() {
        return cur_time - last_time;
    }
};


class CPad
{
private:
    int DevID = -1;
    int dwPacketNumber_last;
    int vibration_duration;
    bool vibrate = 0;
    Ctimer vibration_timer;
    XINPUT_VIBRATION vibration;
public:
    XINPUT_STATE state;

    CPad();
    bool CheckInput();
    void SetVibration(int lMotor, int rMotor, int vibration_duration);
    void ProcVibration();
    void UpdateVibrationTimer();
};

CPad.cpp:

#include "CPad.h"

CPad::CPad()
{
    for (int i = 0; i < XUSER_MAX_COUNT; i++)
    {
        XINPUT_STATE tmp;
        ZeroMemory(&tmp, sizeof(XINPUT_STATE));
        if (XInputGetState(i, &tmp) == ERROR_SUCCESS)
        {
            DevID = i;
            state = tmp;
        }
    }
    if (DevID == -1)
    {
        cerr << "Error: couldn't find Controller" << endl;
        delete(this);
        exit(1);
    }

    dwPacketNumber_last = state.dwPacketNumber;
}

bool CPad::CheckInput()
{
    dwPacketNumber_last = state.dwPacketNumber;
    XInputGetState(DevID, &state);

    if (dwPacketNumber_last != state.dwPacketNumber)
    {
        dwPacketNumber_last = state.dwPacketNumber;
        return true;
    }
    else
    {
        return false;
    }
}

void CPad::SetVibration(int lMotor, int rMotor, int vibration_duration)
{
    this->vibration_duration = vibration_duration;
    vibrate = true;

    vibration.wLeftMotorSpeed = lMotor;
    vibration.wRightMotorSpeed = rMotor;

    XInputSetState(DevID, &vibration);
}

void CPad::ProcVibration()
{
    if (vibrate)
    {
        if (vibration_timer.GetElapsed() > vibration_duration)
        {
            vibration_timer.reset();
            vibrate = false;

            vibration.wLeftMotorSpeed = 0;
            vibration.wRightMotorSpeed = 0;

            XInputSetState(DevID, &vibration);
        }
    }
}

void CPad::UpdateVibrationTimer()
{
    vibration_timer.update();
}

的main.cpp

#include "CPad.h"

int main(int argc, char **argv)
{
    bool run = true;

    CPad pad;

    while (run)
    {
        pad.ProcVibration();
        pad.UpdateVibrationTimer();

        if (pad.CheckInput())
        {
            switch (pad.state.Gamepad.wButtons)
            {
            case(XINPUT_GAMEPAD_A):
            {
                cout << "Pressed A" << endl;
                pad.SetVibration(INT_MAX, INT_MAX, 300);
                break;
            }
            case(XINPUT_GAMEPAD_BACK):
            {
                run = false;
                break;
            }
            }
        }

    }

    return 0;
}

0 个答案:

没有答案