Merge branch 'master' into shader-decomp

This commit is contained in:
wheremyfoodat 2024-08-19 22:19:13 +03:00
commit 1366e7a76e
19 changed files with 305 additions and 18 deletions

View file

@ -627,5 +627,6 @@ namespace Audio {
rateMultiplier = 1.f;
buffers = {};
currentSamples.clear();
}
} // namespace Audio

View file

@ -35,6 +35,7 @@ void HIDService::reset() {
circlePadX = circlePadY = 0;
touchScreenX = touchScreenY = 0;
roll = pitch = yaw = 0;
accelX = accelY = accelZ = 0;
}
void HIDService::handleSyncRequest(u32 messagePointer) {
@ -103,7 +104,6 @@ void HIDService::getGyroscopeLowCalibrateParam(u32 messagePointer) {
void HIDService::getGyroscopeCoefficient(u32 messagePointer) {
log("HID::GetGyroscopeLowRawToDpsCoefficient\n");
constexpr float gyroscopeCoeff = 14.375f; // Same as retail 3DS
mem.write32(messagePointer, IPC::responseHeader(0x15, 2, 0));
mem.write32(messagePointer + 4, Result::Success);
mem.write32(messagePointer + 8, Helpers::bit_cast<u32, float>(gyroscopeCoeff));
@ -190,6 +190,20 @@ void HIDService::updateInputs(u64 currentTick) {
writeSharedMem<u64>(0x108, currentTick); // Write new tick count
}
writeSharedMem<u32>(0x118, nextAccelerometerIndex); // Index last updated by the HID module
const size_t accelEntryOffset = 0x128 + (nextAccelerometerIndex * 6); // Offset in the array of 8 accelerometer entries
// Raw data of current accelerometer entry
// TODO: How is the "raw" data actually calculated?
s16* accelerometerDataRaw = getSharedMemPointer<s16>(0x120);
accelerometerDataRaw[0] = accelX;
accelerometerDataRaw[1] = accelY;
accelerometerDataRaw[2] = accelZ;
// Accelerometer entry in entry table
s16* accelerometerData = getSharedMemPointer<s16>(accelEntryOffset);
accelerometerData[0] = accelX;
accelerometerData[1] = accelY;
accelerometerData[2] = accelZ;
nextAccelerometerIndex = (nextAccelerometerIndex + 1) % 8; // Move to next entry
// Next, update gyro state
@ -198,9 +212,10 @@ void HIDService::updateInputs(u64 currentTick) {
writeSharedMem<u64>(0x158, currentTick); // Write new tick count
}
const size_t gyroEntryOffset = 0x178 + (nextGyroIndex * 6); // Offset in the array of 8 touchscreen entries
writeSharedMem<u16>(gyroEntryOffset, pitch);
writeSharedMem<u16>(gyroEntryOffset + 2, yaw);
writeSharedMem<u16>(gyroEntryOffset + 4, roll);
s16* gyroData = getSharedMemPointer<s16>(gyroEntryOffset);
gyroData[0] = pitch;
gyroData[1] = yaw;
gyroData[2] = roll;
// Since gyroscope euler angles are relative, we zero them out here and the frontend will update them again when we receive a new rotation
roll = pitch = yaw = 0;

View file

@ -1,6 +1,6 @@
#include "emulator.hpp"
#ifndef __ANDROID__
#if !defined(__ANDROID__) && !defined(__LIBRETRO__)
#include <SDL_filesystem.h>
#endif

View file

@ -372,7 +372,7 @@ uint retro_api_version() { return RETRO_API_VERSION; }
usize retro_get_memory_size(uint id) {
if (id == RETRO_MEMORY_SYSTEM_RAM) {
return 0;
return Memory::FCRAM_SIZE;
}
return 0;
@ -380,7 +380,7 @@ usize retro_get_memory_size(uint id) {
void* retro_get_memory_data(uint id) {
if (id == RETRO_MEMORY_SYSTEM_RAM) {
return 0;
return emulator->getMemory().getFCRAM();
}
return nullptr;

View file

@ -9,6 +9,7 @@
#include "cheats.hpp"
#include "input_mappings.hpp"
#include "sdl_sensors.hpp"
#include "services/dsp.hpp"
MainWindow::MainWindow(QApplication* app, QWidget* parent) : QMainWindow(parent), keyboardMappings(InputMappings::defaultKeyboardMappings()) {
@ -521,6 +522,8 @@ void MainWindow::initControllers() {
SDL_Joystick* stick = SDL_GameControllerGetJoystick(gameController);
gameControllerID = SDL_JoystickInstanceID(stick);
}
setupControllerSensors(gameController);
}
}
@ -558,6 +561,8 @@ void MainWindow::pollControllers() {
if (gameController == nullptr) {
gameController = SDL_GameControllerOpen(event.cdevice.which);
gameControllerID = event.cdevice.which;
setupControllerSensors(gameController);
}
break;
@ -598,6 +603,37 @@ void MainWindow::pollControllers() {
}
break;
}
case SDL_CONTROLLERSENSORUPDATE: {
if (event.csensor.sensor == SDL_SENSOR_GYRO) {
auto rotation = Sensors::SDL::convertRotation({
event.csensor.data[0],
event.csensor.data[1],
event.csensor.data[2],
});
hid.setPitch(s16(rotation.x));
hid.setRoll(s16(rotation.y));
hid.setYaw(s16(rotation.z));
} else if (event.csensor.sensor == SDL_SENSOR_ACCEL) {
auto accel = Sensors::SDL::convertAcceleration(event.csensor.data);
hid.setAccel(accel.x, accel.y, accel.z);
}
break;
}
}
}
}
void MainWindow::setupControllerSensors(SDL_GameController* controller) {
bool haveGyro = SDL_GameControllerHasSensor(controller, SDL_SENSOR_GYRO) == SDL_TRUE;
bool haveAccelerometer = SDL_GameControllerHasSensor(controller, SDL_SENSOR_ACCEL) == SDL_TRUE;
if (haveGyro) {
SDL_GameControllerSetSensorEnabled(controller, SDL_SENSOR_GYRO, SDL_TRUE);
}
if (haveAccelerometer) {
SDL_GameControllerSetSensorEnabled(controller, SDL_SENSOR_ACCEL, SDL_TRUE);
}
}

View file

@ -2,6 +2,8 @@
#include <glad/gl.h>
#include "sdl_sensors.hpp"
FrontendSDL::FrontendSDL() : keyboardMappings(InputMappings::defaultKeyboardMappings()) {
if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_EVENTS) < 0) {
Helpers::panic("Failed to initialize SDL2");
@ -20,6 +22,8 @@ FrontendSDL::FrontendSDL() : keyboardMappings(InputMappings::defaultKeyboardMapp
SDL_Joystick* stick = SDL_GameControllerGetJoystick(gameController);
gameControllerID = SDL_JoystickInstanceID(stick);
}
setupControllerSensors(gameController);
}
const EmulatorConfig& config = emu.getConfig();
@ -200,6 +204,8 @@ void FrontendSDL::run() {
if (gameController == nullptr) {
gameController = SDL_GameControllerOpen(event.cdevice.which);
gameControllerID = event.cdevice.which;
setupControllerSensors(gameController);
}
break;
@ -280,6 +286,24 @@ void FrontendSDL::run() {
}
break;
}
case SDL_CONTROLLERSENSORUPDATE: {
if (event.csensor.sensor == SDL_SENSOR_GYRO) {
auto rotation = Sensors::SDL::convertRotation({
event.csensor.data[0],
event.csensor.data[1],
event.csensor.data[2],
});
hid.setPitch(s16(rotation.x));
hid.setRoll(s16(rotation.y));
hid.setYaw(s16(rotation.z));
} else if (event.csensor.sensor == SDL_SENSOR_ACCEL) {
auto accel = Sensors::SDL::convertAcceleration(event.csensor.data);
hid.setAccel(accel.x, accel.y, accel.z);
}
break;
}
case SDL_DROPFILE: {
char* droppedDir = event.drop.file;
@ -342,3 +366,16 @@ void FrontendSDL::run() {
SDL_GL_SwapWindow(window);
}
}
void FrontendSDL::setupControllerSensors(SDL_GameController* controller) {
bool haveGyro = SDL_GameControllerHasSensor(controller, SDL_SENSOR_GYRO) == SDL_TRUE;
bool haveAccelerometer = SDL_GameControllerHasSensor(controller, SDL_SENSOR_ACCEL) == SDL_TRUE;
if (haveGyro) {
SDL_GameControllerSetSensorEnabled(controller, SDL_SENSOR_GYRO, SDL_TRUE);
}
if (haveAccelerometer) {
SDL_GameControllerSetSensorEnabled(controller, SDL_SENSOR_ACCEL, SDL_TRUE);
}
}