Skip to content
This repository has been archived by the owner on Mar 1, 2024. It is now read-only.

Enable/disable user input devices #136

Merged
merged 16 commits into from
Mar 6, 2023
Merged
Show file tree
Hide file tree
Changes from 12 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
48 changes: 48 additions & 0 deletions Frontend/library/src/Config/Config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,10 @@ export class Flags {
static StartVideoMuted = 'StartVideoMuted' as const;
static SuppressBrowserKeys = 'SuppressBrowserKeys' as const;
static UseMic = 'UseMic' as const;
static EnableKeyboardInput = 'EnableKeyboardInput' as const;
static EnableMouseInput = 'EnableMouseInput' as const;
static EnableTouchInput = 'EnableTouchInput' as const;
static EnableGamePadInput = 'EnableGamePadInput' as const;
}

export type FlagsKeys = Exclude<keyof typeof Flags, 'prototype'>;
Expand Down Expand Up @@ -398,6 +402,50 @@ export class Config {
)
);

this.flags.set(
Flags.EnableKeyboardInput,
new SettingFlag(
Flags.EnableKeyboardInput,
'Enable keyboard input',
'If enabled, send keyboard events to streamer',
true,
useUrlParams
)
);

this.flags.set(
Flags.EnableMouseInput,
new SettingFlag(
Flags.EnableMouseInput,
'Enable mouse input',
'If enabled, send mouse events to streamer',
true,
useUrlParams
)
);

this.flags.set(
Flags.EnableTouchInput,
new SettingFlag(
Flags.EnableTouchInput,
'Enable touch input',
'If enabled, send touch events to streamer',
true,
useUrlParams
)
);

this.flags.set(
Flags.EnableGamePadInput,
new SettingFlag(
Flags.EnableGamePadInput,
'Enable game pad input',
'If enabled, send game pad events to streamer',
true,
useUrlParams
)
);

hmuurine marked this conversation as resolved.
Show resolved Hide resolved
/**
* Numeric parameters
*/
Expand Down
39 changes: 31 additions & 8 deletions Frontend/library/src/Inputs/FakeTouchController.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import { StreamMessageController } from '../UeInstanceMessage/StreamMessageContr
import { VideoPlayer } from '../VideoPlayer/VideoPlayer';
import { ITouchController } from './ITouchController';
import { MouseButton } from './MouseButtons';
import { EventListenerTracker } from '../Util/EventListenerTracker';

/**
* Allows for the usage of fake touch events and implements ITouchController
Expand All @@ -18,6 +19,9 @@ export class FakeTouchController implements ITouchController {
coordinateConverter: CoordinateConverter;
videoElementParentClientRect: DOMRect;

// Utility for keeping track of event handlers and unregistering them
private touchEventListenerTracker = new EventListenerTracker();

/**
* @param toStreamerMessagesProvider - Stream message instance
* @param videoElementProvider - Video element instance
Expand All @@ -31,9 +35,28 @@ export class FakeTouchController implements ITouchController {
this.toStreamerMessagesProvider = toStreamerMessagesProvider;
this.videoElementProvider = videoElementProvider;
this.coordinateConverter = coordinateConverter;
document.ontouchstart = (ev: TouchEvent) => this.onTouchStart(ev);
document.ontouchend = (ev: TouchEvent) => this.onTouchEnd(ev);
document.ontouchmove = (ev: TouchEvent) => this.onTouchMove(ev);
const ontouchstart = (ev: TouchEvent) => this.onTouchStart(ev);
const ontouchend = (ev: TouchEvent) => this.onTouchEnd(ev);
const ontouchmove = (ev: TouchEvent) => this.onTouchMove(ev);
document.addEventListener('touchstart', ontouchstart, { passive: false });
document.addEventListener('touchend', ontouchend, { passive: false });
document.addEventListener('touchmove', ontouchmove, { passive: false });
this.touchEventListenerTracker.addUnregisterCallback(
() => document.removeEventListener('touchstart', ontouchstart)
);
this.touchEventListenerTracker.addUnregisterCallback(
() => document.removeEventListener('touchend', ontouchend)
);
this.touchEventListenerTracker.addUnregisterCallback(
() => document.removeEventListener('touchmove', ontouchmove)
);
}

/**
* Unregister all touch events
*/
unregisterTouchEvents() {
this.touchEventListenerTracker.unregisterAll();
}

/**
Expand Down Expand Up @@ -62,8 +85,8 @@ export class FakeTouchController implements ITouchController {

const videoElementParent =
this.videoElementProvider.getVideoParentElement() as HTMLDivElement;
const mouseEvent = new MouseEvent(touch.type, first_touch);
videoElementParent.onmouseenter(mouseEvent);
const mouseEvent = new MouseEvent('mouseenter', first_touch);
videoElementParent.dispatchEvent(mouseEvent);

const coord = this.coordinateConverter.normalizeAndQuantizeUnsigned(
this.fakeTouchFinger.x,
Expand Down Expand Up @@ -107,8 +130,8 @@ export class FakeTouchController implements ITouchController {
coord.y
]);

const mouseEvent = new MouseEvent(touchEvent.type, touch);
videoElementParent.onmouseleave(mouseEvent);
const mouseEvent = new MouseEvent('mouseleave', touch);
videoElementParent.dispatchEvent(mouseEvent);
this.fakeTouchFinger = null;
break;
}
Expand Down Expand Up @@ -140,7 +163,7 @@ export class FakeTouchController implements ITouchController {
x - this.fakeTouchFinger.x,
y - this.fakeTouchFinger.y
);
toStreamerHandlers.get('MoveMouse')([
toStreamerHandlers.get('MouseMove')([
hmuurine marked this conversation as resolved.
Show resolved Hide resolved
coord.x,
coord.y,
delta.x,
Expand Down
56 changes: 42 additions & 14 deletions Frontend/library/src/Inputs/GamepadController.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

import { Logger } from '../Logger/Logger';
import { StreamMessageController } from '../UeInstanceMessage/StreamMessageController';
import { EventListenerTracker } from '../Util/EventListenerTracker';
import { Controller } from './GamepadTypes';

/**
Expand All @@ -12,35 +13,60 @@ export class GamePadController {
requestAnimationFrame: (callback: FrameRequestCallback) => number;
toStreamerMessagesProvider: StreamMessageController;

// Utility for keeping track of event handlers and unregistering them
private gamePadEventListenerTracker = new EventListenerTracker();

/**
* @param toStreamerMessagesProvider - Stream message instance
*/
constructor(toStreamerMessagesProvider: StreamMessageController) {
this.toStreamerMessagesProvider = toStreamerMessagesProvider;

this.requestAnimationFrame =
this.requestAnimationFrame = (
window.mozRequestAnimationFrame ||
window.webkitRequestAnimationFrame ||
window.requestAnimationFrame;
window.requestAnimationFrame
).bind(window);
const browserWindow = window as Window;
if ('GamepadEvent' in browserWindow) {
window.addEventListener('gamepadconnected', (ev: GamepadEvent) =>
this.gamePadConnectHandler(ev)
const onGamePadConnected = (ev: GamepadEvent) =>
this.gamePadConnectHandler(ev);
const onGamePadDisconnected = (ev: GamepadEvent) =>
this.gamePadDisconnectHandler(ev);
window.addEventListener('gamepadconnected', onGamePadConnected);
window.addEventListener('gamepaddisconnected', onGamePadDisconnected);
this.gamePadEventListenerTracker.addUnregisterCallback(
() => window.removeEventListener('gamepadconnected', onGamePadConnected)
);
window.addEventListener('gamepaddisconnected', (ev: GamepadEvent) =>
this.gamePadDisconnectHandler(ev)
this.gamePadEventListenerTracker.addUnregisterCallback(
() => window.removeEventListener('gamepaddisconnected', onGamePadDisconnected)
);
} else if ('WebKitGamepadEvent' in browserWindow) {
window.addEventListener(
'webkitgamepadconnected',
(ev: GamepadEvent) => this.gamePadConnectHandler(ev)
const onWebkitGamePadConnected = (ev: GamepadEvent) => this.gamePadConnectHandler(ev);
const onWebkitGamePadDisconnected = (ev: GamepadEvent) => this.gamePadDisconnectHandler(ev);
window.addEventListener('webkitgamepadconnected', onWebkitGamePadConnected);
window.addEventListener('webkitgamepaddisconnected', onWebkitGamePadDisconnected);
this.gamePadEventListenerTracker.addUnregisterCallback(
() => window.removeEventListener('webkitgamepadconnected', onWebkitGamePadConnected)
);
window.addEventListener(
'webkitgamepaddisconnected',
(ev: GamepadEvent) => this.gamePadDisconnectHandler(ev)
this.gamePadEventListenerTracker.addUnregisterCallback(
() => window.removeEventListener('webkitgamepaddisconnected', onWebkitGamePadDisconnected)
);
}
this.controllers = [];
for (const gamepad of navigator.getGamepads()) {
if (gamepad) {
this.gamePadConnectHandler(new GamepadEvent('gamepadconnected', { gamepad }));
}
}
}

/**
* Unregisters all event handlers
*/
unregisterGamePadEvents() {
this.gamePadEventListenerTracker.unregisterAll();
this.controllers = [];
}

/**
Expand All @@ -64,7 +90,7 @@ export class GamePadController {
'gamepad: ' + gamepad.id + ' connected',
6
);
window.requestAnimationFrame(() => this.updateStatus());
this.requestAnimationFrame(() => this.updateStatus());
}

/**
Expand Down Expand Up @@ -185,7 +211,9 @@ export class GamePadController {
}
this.controllers[controllerIndex].prevState = currentState;
}
this.requestAnimationFrame(() => this.updateStatus());
hmuurine marked this conversation as resolved.
Show resolved Hide resolved
if (this.controllers.length > 0) {
this.requestAnimationFrame(() => this.updateStatus());
}
}
}

Expand Down
7 changes: 7 additions & 0 deletions Frontend/library/src/Inputs/HoveringMouseEvents.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,13 @@ export class HoveringMouseEvents implements IMouseEvents {
this.mouseController = mouseController;
}

/**
* Unregister event handlers
*/
unregisterMouseEvents(): void {
// empty for HoveringMouseEvents implementation
}

/**
* Handle the mouse move event, sends the mouse data to the UE Instance
* @param mouseEvent - Mouse Event
Expand Down
5 changes: 5 additions & 0 deletions Frontend/library/src/Inputs/IMouseEvents.ts
Original file line number Diff line number Diff line change
Expand Up @@ -56,4 +56,9 @@ export interface IMouseEvents {
* @param mouseEvent - mouse event
*/
handleContextMenu?(mouseEvent: MouseEvent): void;

/**
* Unregisters any registered mouse event handlers
*/
unregisterMouseEvents(): void;
}
5 changes: 5 additions & 0 deletions Frontend/library/src/Inputs/ITouchController.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,4 +21,9 @@ export interface ITouchController {
* @param touchEvent - Touch Event Data
*/
onTouchMove(touchEvent: TouchEvent): void;

/**
* Unregisters all touch event handlers
*/
unregisterTouchEvents(): void;
}
Loading