pydualsense icon indicating copy to clipboard operation
pydualsense copied to clipboard

the sixaxis data is unreadable

Open South-River opened this issue 2 years ago • 4 comments

I don't know if the data is correct. The data jumps very violently. The value sum of squares of the accelerometer in the static state has a large jump. However, it should not undergo a large jump under static conditions. At the same time, there is no problem with my gamepad, because the data it reads in ds4windows behaves normally

South-River avatar Feb 13 '23 16:02 South-River

After I read the DS4Windows->DS4Windows->DS4Library->DualSenseDevice.cs file, I found that the problem comes from the wrong order of reading the gyro and accelerometer. In DS4Windows, gyro and accel are read like this


                    fixed (byte* pbInput = &inputReport[16+reportOffset], pbGyro = gyro, pbAccel = accel)
                    {
                        for (int i = 0; i < 6; i++)
                        {
                            pbGyro[i] = pbInput[i];
                        }

                        for (int i = 6; i < 12; i++)
                        {
                            pbAccel[i - 6] = pbInput[i];
                        }

                        if (synced)
                        {
                            sixAxis.handleSixaxis(pbGyro, pbAccel, cState, elapsedDeltaTime);
                        }
                    }

But in pydualsense.py, they are read like this

        # accelerometer
        self.state.accelerometer.X = int.from_bytes(([inReport[16], inReport[17]]), byteorder='little', signed=True)
        self.state.accelerometer.Y = int.from_bytes(([inReport[18], inReport[19]]), byteorder='little', signed=True)
        self.state.accelerometer.Z = int.from_bytes(([inReport[20], inReport[21]]), byteorder='little', signed=True)

        # gyrometer
        self.state.gyro.Pitch = int.from_bytes(([inReport[22], inReport[23]]), byteorder='little', signed=True)
        self.state.gyro.Yaw = int.from_bytes(([inReport[24], inReport[25]]), byteorder='little', signed=True)
        self.state.gyro.Roll = int.from_bytes(([inReport[26], inReport[27]]), byteorder='little', signed=True)

I got the correct data after adjusting their order.

But another problem in BT connection type, they (as well as trackpad) shouldn't be directly read from inReport, so I think the code should be changed like this

        # trackpad touch
        self.state.trackPadTouch0.ID = states[33] & 0x7F
        self.state.trackPadTouch0.isActive = (states[33] & 0x80) == 0
        self.state.trackPadTouch0.X = ((states[35] & 0x0f) << 8) | (states[34])
        self.state.trackPadTouch0.Y = ((states[36]) << 4) | ((states[35] & 0xf0) >> 4)

        # trackpad touch
        self.state.trackPadTouch1.ID = states[37] & 0x7F
        self.state.trackPadTouch1.isActive = (states[37] & 0x80) == 0
        self.state.trackPadTouch1.X = ((states[39] & 0x0f) << 8) | (states[38])
        self.state.trackPadTouch1.Y = ((states[40]) << 4) | ((states[39] & 0xf0) >> 4)

        # gyro
        self.state.gyro.Pitch = int.from_bytes(([states[16], states[17]]), byteorder='little', signed=True)
        self.state.gyro.Yaw = int.from_bytes(([states[18], states[19]]), byteorder='little', signed=True)
        self.state.gyro.Roll = int.from_bytes(([states[20], states[21]]), byteorder='little', signed=True)

        # accelerometer
        self.state.accelerometer.X = int.from_bytes(([states[22], states[23]]), byteorder='little', signed=True)
        self.state.accelerometer.Y = int.from_bytes(([states[24], states[25]]), byteorder='little', signed=True)
        self.state.accelerometer.Z = int.from_bytes(([states[26], states[27]]), byteorder='little', signed=True)

South-River avatar Feb 14 '23 04:02 South-River

since the imu has noise and zero-offset. i think it would be better to give a function for users to calibrate it.

South-River avatar Feb 14 '23 06:02 South-River

since the imu has noise and zero-offset. i think it would be better to give a function for users to calibrate it.

what diffrence would that make? the states variable would still be overwritten in the next calling. reading from states wouldn't make any diffrence

flok avatar Feb 16 '23 19:02 flok

what diffrence would that make? the states variable would still be overwritten in the next calling. reading from states wouldn't make any diffrence

Performing parameter calibration can make the obtained imu data more accurate. Although the output value of the sensor will not change, the output of the algorithm for calculating the gamepad pose can be made more accurate after removing the zero offset.

South-River avatar Feb 18 '23 13:02 South-River