window manager HID list

This commit is contained in:
nakst 2021-10-12 20:54:19 +01:00
parent fe78d0a16e
commit cc66d80a25
7 changed files with 106 additions and 42 deletions

View File

@ -77,6 +77,12 @@ Once complete, you can test the operating system in an emulator.
* If you have Qemu installed, run `t2` in the build system.
* If you have VirtualBox installed, make a 128MB drive called `vbox.vdi` in the `bin` folder, attach it to a virtual machine called "Essence" (choose "Windows 7 64-bit" as the OS), and run `v` in the build system.
## Keyboard layout
To set the default keyboard layout for use in the emulator to match your current one, run:
setxkbmap -query | grep layout | awk '{OFS=""; print "General.keyboard_layout=", $2}' >> bin/config.ini
## Configuration
From within the build system, run the command `config` to open the configuration editor. Click an option to change its value, and then click the `Save` button. You changes are saved locally, and will not be uploaded by Git. Not all configurations are likely to work; if you don't know what you're doing, it's probably best to stick with the defaults.

View File

@ -558,8 +558,8 @@ void PS2::Initialise(KDevice *parentDevice) {
}
KDevice *controller = KDeviceCreate("PS/2 controller", parentDevice, sizeof(KDevice));
KDeviceSendConnectedMessage(KDeviceCreate("PS/2 keyboard", controller, sizeof(KDevice)), ES_DEVICE_KEYBOARD);
if (channels == 2) KDeviceCreate("PS/2 mouse", controller, sizeof(KDevice));
KRegisterHIDevice((KHIDevice *) KDeviceCreate("PS/2 keyboard", controller, sizeof(KHIDevice)));
if (channels == 2) KRegisterHIDevice((KHIDevice *) KDeviceCreate("PS/2 mouse", controller, sizeof(KHIDevice)));
KernelLog(LOG_INFO, "PS/2", "controller initialised", "Setup PS/2 controller%z.\n", channels == 2 ? ", with a mouse" : "");
}

View File

@ -41,7 +41,7 @@ struct GameController {
uint8_t reportPrefix;
};
struct HIDDevice : KDevice {
struct HIDDevice : KHIDevice {
KUSBDevice *device;
Array<ReportItem, K_FIXED> reportItems;
@ -771,7 +771,7 @@ static void DeviceAttach(KDevice *parent) {
device->destroy = DeviceDestroy;
device->device = (KUSBDevice *) parent;
device->Initialise();
KDeviceCloseHandle(device);
KRegisterHIDevice(device);
}
KDriver driverUSBHID = {

View File

@ -360,34 +360,6 @@ struct KTimer {
void KTimerSet(KTimer *timer, uint64_t triggerInMs, KAsyncTaskCallback callback = nullptr, EsGeneric argument = 0);
void KTimerRemove(KTimer *timer); // Timers with callbacks cannot be removed (it'd race with async task delivery).
// ---------------------------------------------------------------------------------------------------------------
// Window manager.
// ---------------------------------------------------------------------------------------------------------------
struct KMouseUpdateData {
int32_t xMovement, yMovement;
bool xIsAbsolute, yIsAbsolute;
int32_t xFrom, xTo, yFrom, yTo;
int32_t xScroll, yScroll;
uint32_t buttons;
};
#define K_CURSOR_MOVEMENT_SCALE (0x100)
void KMouseUpdate(const KMouseUpdateData *data);
void KKeyboardUpdate(uint16_t *keysDown, size_t keysDownCount);
void KKeyPress(uint32_t scancode);
uint64_t KGameControllerConnect();
void KGameControllerDisconnect(uint64_t id);
void KGameControllerUpdate(EsGameControllerState *state);
#define K_SCANCODE_KEY_RELEASED (1 << 15)
#define K_SCANCODE_KEY_PRESSED (0 << 15)
#define K_LEFT_BUTTON (1)
#define K_MIDDLE_BUTTON (2)
#define K_RIGHT_BUTTON (4)
// ---------------------------------------------------------------------------------------------------------------
// Memory manager.
// ---------------------------------------------------------------------------------------------------------------
@ -623,6 +595,45 @@ size_t KDMABufferGetTotalByteCount(KDMABuffer *buffer);
KDMASegment KDMABufferNextSegment(KDMABuffer *buffer, bool peek = false);
bool KDMABufferIsComplete(KDMABuffer *buffer); // Returns true if the end of the transfer buffer has been reached.
// ---------------------------------------------------------------------------------------------------------------
// Window manager.
// ---------------------------------------------------------------------------------------------------------------
struct KMouseUpdateData {
#define K_CURSOR_MOVEMENT_SCALE (0x100)
int32_t xMovement, yMovement;
bool xIsAbsolute, yIsAbsolute;
int32_t xFrom, xTo, yFrom, yTo;
int32_t xScroll, yScroll;
#define K_LEFT_BUTTON (1)
#define K_MIDDLE_BUTTON (2)
#define K_RIGHT_BUTTON (4)
uint32_t buttons;
};
struct KHIDevice : KDevice {
#define K_KEYBOARD_INDICATOR_NUM_LOCK (1 << 0)
#define K_KEYBOARD_INDICATOR_CAPS_LOCK (1 << 1)
#define K_KEYBOARD_INDICATOR_SCROLL_LOCK (1 << 2)
#define K_KEYBOARD_INDICATOR_COMPOSE (1 << 3)
#define K_KEYBOARD_INDICATOR_KANA (1 << 4)
#define K_KEYBOARD_INDICATOR_SHIFT (1 << 5)
void (*setKeyboardIndicators)(KHIDevice *device, uint32_t indicators);
};
void KMouseUpdate(const KMouseUpdateData *data);
#define K_SCANCODE_KEY_RELEASED (1 << 15)
#define K_SCANCODE_KEY_PRESSED (0 << 15)
void KKeyPress(uint32_t scancode);
void KKeyboardUpdate(uint16_t *keysDown, size_t keysDownCount);
uint64_t KGameControllerConnect();
void KGameControllerDisconnect(uint64_t id);
void KGameControllerUpdate(EsGameControllerState *state);
void KRegisterHIDevice(KHIDevice *device);
// ---------------------------------------------------------------------------------------------------------------
// Block devices.
// ---------------------------------------------------------------------------------------------------------------

View File

@ -1182,10 +1182,10 @@ SYSCALL_IMPLEMENT(ES_SYSCALL_GAME_CONTROLLER_STATE_POLL) {
EsGameControllerState gameControllers[ES_GAME_CONTROLLER_MAX_COUNT];
size_t gameControllerCount;
KMutexAcquire(&windowManager.gameControllersMutex);
KMutexAcquire(&windowManager.deviceMutex);
gameControllerCount = windowManager.gameControllerCount;
EsMemoryCopy(gameControllers, windowManager.gameControllers, sizeof(EsGameControllerState) * gameControllerCount);
KMutexRelease(&windowManager.gameControllersMutex);
KMutexRelease(&windowManager.deviceMutex);
SYSCALL_WRITE(argument0, gameControllers, sizeof(EsGameControllerState) * gameControllerCount);
SYSCALL_RETURN(gameControllerCount, false);

View File

@ -128,9 +128,12 @@ struct WindowManager {
EsRectangle workArea;
// Game controllers:
// Devices:
KMutex deviceMutex;
Array<KDevice *, K_FIXED> hiDevices;
KMutex gameControllersMutex;
EsGameControllerState gameControllers[ES_GAME_CONTROLLER_MAX_COUNT];
size_t gameControllerCount;
EsObjectID gameControllerID;
@ -155,6 +158,44 @@ void SendMessageToWindow(Window *window, EsMessage *message);
#else
void HIDeviceUpdateIndicators() {
KMutexAssertLocked(&windowManager.mutex);
KMutexAcquire(&windowManager.deviceMutex);
// TODO Other indicators.
uint32_t indicators = windowManager.numlock ? K_KEYBOARD_INDICATOR_NUM_LOCK : 0;
for (uintptr_t i = 0; i < windowManager.hiDevices.Length(); i++) {
KHIDevice *device = (KHIDevice *) windowManager.hiDevices[i]->parent;
if (device->setKeyboardIndicators) {
device->setKeyboardIndicators(device, indicators);
}
}
KMutexRelease(&windowManager.deviceMutex);
}
void HIDeviceRemoved(KDevice *device) {
KMutexAcquire(&windowManager.deviceMutex);
windowManager.hiDevices.FindAndDeleteSwap(device, true);
KMutexRelease(&windowManager.deviceMutex);
}
void KRegisterHIDevice(KHIDevice *device) {
KDevice *child = KDeviceCreate("HID child", device, sizeof(KDevice));
if (child) {
KMutexAcquire(&windowManager.deviceMutex);
child->removed = HIDeviceRemoved;
windowManager.hiDevices.Add(child);
KMutexRelease(&windowManager.deviceMutex);
KDeviceCloseHandle(child);
}
KDeviceCloseHandle(device);
}
bool Window::IsVisible() {
return !hidden && !closed && (id != windowManager.eyedropAvoidID || !windowManager.eyedropping);
}
@ -321,6 +362,11 @@ void WindowManager::PressKey(unsigned scancode) {
if (scancode == ES_SCANCODE_RIGHT_FLAG) flag2 = true;
if (scancode == (ES_SCANCODE_RIGHT_FLAG | K_SCANCODE_KEY_RELEASED)) flag2 = false;
if (scancode == ES_SCANCODE_NUM_LOCK) {
numlock = !numlock;
HIDeviceUpdateIndicators();
}
modifiers = (alt ? ES_MODIFIER_ALT : 0)
| (alt2 ? ES_MODIFIER_ALT_GR : 0)
| ((ctrl | ctrl2) ? ES_MODIFIER_CTRL : 0)
@ -1310,7 +1356,7 @@ void KKeyboardUpdate(uint16_t *keysDown, size_t keysDownCount) {
}
uint64_t KGameControllerConnect() {
KMutexAcquire(&windowManager.gameControllersMutex);
KMutexAcquire(&windowManager.deviceMutex);
EsObjectID id = ++windowManager.gameControllerID;
@ -1320,13 +1366,13 @@ uint64_t KGameControllerConnect() {
id = 0;
}
KMutexRelease(&windowManager.gameControllersMutex);
KMutexRelease(&windowManager.deviceMutex);
return id;
}
void KGameControllerDisconnect(uint64_t id) {
KMutexAcquire(&windowManager.gameControllersMutex);
KMutexAcquire(&windowManager.deviceMutex);
for (uintptr_t i = 0; i < windowManager.gameControllerCount; i++) {
if (windowManager.gameControllers[i].id == id) {
@ -1338,11 +1384,11 @@ void KGameControllerDisconnect(uint64_t id) {
}
}
KMutexRelease(&windowManager.gameControllersMutex);
KMutexRelease(&windowManager.deviceMutex);
}
void KGameControllerUpdate(EsGameControllerState *state) {
KMutexAcquire(&windowManager.gameControllersMutex);
KMutexAcquire(&windowManager.deviceMutex);
for (uintptr_t i = 0; i < windowManager.gameControllerCount; i++) {
if (windowManager.gameControllers[i].id == state->id) {
@ -1356,7 +1402,7 @@ void KGameControllerUpdate(EsGameControllerState *state) {
}
}
KMutexRelease(&windowManager.gameControllersMutex);
KMutexRelease(&windowManager.deviceMutex);
}
#endif

View File

@ -320,6 +320,7 @@ Option options[] = {
{ "General.wallpaper", OPTION_TYPE_STRING, { .s = NULL } },
{ "General.installation_state", OPTION_TYPE_STRING, { .s = "0" } },
{ "General.ui_scale", OPTION_TYPE_STRING, { .s = "100" } },
{ "General.keyboard_layout", OPTION_TYPE_STRING, { .s = "us" } },
};
char *previousOptionsBuffer;