feat(input): add absolute pointer and scroll

This commit is contained in:
sechmachine
2026-08-11 01:09:42 +07:00
parent bfffea5d2d
commit f981823909
10 changed files with 285 additions and 34 deletions
+39
View File
@@ -15,6 +15,8 @@ const (
gatewayInputRelative = 3
gatewayInputUTF8 = 4
gatewayInputController = 5
gatewayInputAbsolute = 6
gatewayInputScroll = 7
)
func EncodeInputEvent(event InputEvent) ([]byte, error) {
@@ -76,6 +78,24 @@ func EncodeInputEvent(event InputEvent) ([]byte, error) {
encoded[4], encoded[5], encoded[6] = gatewayInputController, 17, byte(event.Code)
copy(encoded[7:], event.Payload)
return encoded, nil
case "mouse-absolute":
if event.Pressed || event.Code != 0 || !validAbsolutePayload(event.Payload) {
return nil, ErrInputMalformed
}
encoded := make([]byte, gatewayInputHeaderSize+8)
copy(encoded, "VGI1")
encoded[4], encoded[5] = gatewayInputAbsolute, 8
copy(encoded[6:], event.Payload)
return encoded, nil
case "mouse-scroll":
if event.Pressed || event.Code != 0 || len(event.Payload) != 4 {
return nil, ErrInputMalformed
}
encoded := make([]byte, gatewayInputHeaderSize+4)
copy(encoded, "VGI1")
encoded[4], encoded[5] = gatewayInputScroll, 4
copy(encoded[6:], event.Payload)
return encoded, nil
default:
return nil, ErrInputMalformed
}
@@ -117,11 +137,30 @@ func DecodeInputEvent(data []byte) (InputEvent, error) {
return InputEvent{}, ErrInputMalformed
}
return InputEvent{Device: "controller", Code: int32(body[0]), Pressed: active != 0, Payload: payload}, nil
case gatewayInputAbsolute:
if !validAbsolutePayload(body) {
return InputEvent{}, ErrInputMalformed
}
return InputEvent{Device: "mouse-absolute", Payload: append([]byte(nil), body...)}, nil
case gatewayInputScroll:
if len(body) != 4 {
return InputEvent{}, ErrInputMalformed
}
return InputEvent{Device: "mouse-scroll", Payload: append([]byte(nil), body...)}, nil
default:
return InputEvent{}, ErrInputMalformed
}
}
func validAbsolutePayload(payload []byte) bool {
if len(payload) != 8 {
return false
}
x, y := binary.BigEndian.Uint16(payload[:2]), binary.BigEndian.Uint16(payload[2:4])
width, height := binary.BigEndian.Uint16(payload[4:6]), binary.BigEndian.Uint16(payload[6:8])
return width != 0 && height != 0 && x < width && y < height
}
func anyNonzero(data []byte) bool {
for _, value := range data {
if value != 0 {