input: add gem ds3 config file

No sticks yet
This commit is contained in:
Megamouse 2023-05-20 15:05:44 +02:00
parent e7c0df4eac
commit 36831a3d6a
3 changed files with 159 additions and 22 deletions

View File

@ -6,6 +6,7 @@
#include "Emu/Cell/PPUModule.h" #include "Emu/Cell/PPUModule.h"
#include "Emu/Cell/timers.hpp" #include "Emu/Cell/timers.hpp"
#include "Emu/Io/MouseHandler.h" #include "Emu/Io/MouseHandler.h"
#include "Emu/Io/gem_config.h"
#include "Emu/system_config.h" #include "Emu/system_config.h"
#include "Emu/System.h" #include "Emu/System.h"
#include "Emu/IdManager.h" #include "Emu/IdManager.h"
@ -140,6 +141,7 @@ public:
static constexpr auto thread_name = "Gem Thread"sv; static constexpr auto thread_name = "Gem Thread"sv;
cfg_gems gem_cfg;
atomic_t<u8> state = 0; atomic_t<u8> state = 0;
struct gem_color struct gem_color
@ -286,7 +288,13 @@ public:
} }
} }
gem_config_data() = default; gem_config_data()
{
if (!gem_cfg.load())
{
cellGem.notice("Could not load gem config. Using defaults.");
}
};
SAVESTATE_INIT_POS(15); SAVESTATE_INIT_POS(15);
@ -318,6 +326,11 @@ public:
gem_config_data(utils::serial& ar) gem_config_data(utils::serial& ar)
{ {
save(ar); save(ar);
if (!ar.is_writing() && !gem_cfg.load())
{
cellGem.notice("Could not load gem config. Using defaults.");
}
} }
}; };
@ -635,6 +648,9 @@ static void ds3_input_to_pad(const u32 port_no, be_t<u16>& digital_buttons, be_t
return; return;
} }
const auto& gem = g_fxo->get<gem_config>();
const auto& cfg = ::at32(gem.gem_cfg.players, port_no);
for (const Button& button : pad->m_buttons) for (const Button& button : pad->m_buttons)
{ {
if (!button.m_pressed) if (!button.m_pressed)
@ -642,46 +658,35 @@ static void ds3_input_to_pad(const u32 port_no, be_t<u16>& digital_buttons, be_t
continue; continue;
} }
// here we check btns, and set pad accordingly if (const auto btn = cfg->find_button(button.m_offset, button.m_outKeyCode))
if (button.m_offset == CELL_PAD_BTN_OFFSET_DIGITAL1)
{ {
switch (button.m_outKeyCode) switch (btn.value())
{ {
case CELL_PAD_CTRL_START: case gem_btn::start:
digital_buttons |= CELL_GEM_CTRL_START; digital_buttons |= CELL_GEM_CTRL_START;
break; break;
case CELL_PAD_CTRL_SELECT: case gem_btn::select:
digital_buttons |= CELL_GEM_CTRL_SELECT; digital_buttons |= CELL_GEM_CTRL_SELECT;
break; break;
default: case gem_btn::square:
break;
}
}
else if (button.m_offset == CELL_PAD_BTN_OFFSET_DIGITAL2)
{
switch (button.m_outKeyCode)
{
case CELL_PAD_CTRL_SQUARE:
digital_buttons |= CELL_GEM_CTRL_SQUARE; digital_buttons |= CELL_GEM_CTRL_SQUARE;
break; break;
case CELL_PAD_CTRL_CROSS: case gem_btn::cross:
digital_buttons |= CELL_GEM_CTRL_CROSS; digital_buttons |= CELL_GEM_CTRL_CROSS;
break; break;
case CELL_PAD_CTRL_CIRCLE: case gem_btn::circle:
digital_buttons |= CELL_GEM_CTRL_CIRCLE; digital_buttons |= CELL_GEM_CTRL_CIRCLE;
break; break;
case CELL_PAD_CTRL_TRIANGLE: case gem_btn::triangle:
digital_buttons |= CELL_GEM_CTRL_TRIANGLE; digital_buttons |= CELL_GEM_CTRL_TRIANGLE;
break; break;
case CELL_PAD_CTRL_R1: case gem_btn::move:
digital_buttons |= CELL_GEM_CTRL_MOVE; digital_buttons |= CELL_GEM_CTRL_MOVE;
break; break;
case CELL_PAD_CTRL_R2: case gem_btn::t:
digital_buttons |= CELL_GEM_CTRL_T; digital_buttons |= CELL_GEM_CTRL_T;
analog_t = std::max<u16>(analog_t, button.m_value); analog_t = std::max<u16>(analog_t, button.m_value);
break; break;
default:
break;
} }
} }
} }

View File

@ -0,0 +1,81 @@
#include "stdafx.h"
#include "gem_config.h"
LOG_CHANNEL(cellGem);
std::optional<gem_btn> cfg_gem::find_button(u32 offset, u32 keycode) const
{
if (const auto it = buttons.find(offset); it != buttons.cend())
{
if (const auto it2 = it->second.find(keycode); it2 != it->second.cend())
{
return it2->second;
}
}
return std::nullopt;
}
bool cfg_gems::load()
{
bool result = false;
const std::string cfg_name = fs::get_config_dir() + "config/gem.yml";
cellGem.notice("Loading gem config: %s", cfg_name);
from_default();
for (cfg_gem* player : players)
{
player->buttons.clear();
}
if (fs::file cfg_file{ cfg_name, fs::read })
{
if (std::string content = cfg_file.to_string(); !content.empty())
{
result = from_string(content);
}
}
else
{
save();
}
for (cfg_gem* player : players)
{
const auto set_button = [&player](pad_button pbtn, gem_btn bbtn)
{
const u32 offset = pad_button_offset(pbtn);
const u32 keycode = pad_button_keycode(pbtn);
player->buttons[(offset >> 8) & 0xFF][keycode & 0xFF] = bbtn;
};
set_button(player->start, gem_btn::start);
set_button(player->select, gem_btn::select);
set_button(player->triangle, gem_btn::triangle);
set_button(player->circle, gem_btn::circle);
set_button(player->cross, gem_btn::cross);
set_button(player->square, gem_btn::square);
set_button(player->move, gem_btn::move);
set_button(player->t, gem_btn::t);
}
return result;
}
void cfg_gems::save() const
{
const std::string cfg_name = fs::get_config_dir() + "config/gem.yml";
cellGem.notice("Saving gem config to '%s'", cfg_name);
if (!fs::create_path(fs::get_parent_dir(cfg_name)))
{
cellGem.fatal("Failed to create path: %s (%s)", cfg_name, fs::g_tls_error);
}
fs::pending_file cfg_file(cfg_name);
if (!cfg_file.file || (cfg_file.file.write(to_string()), !cfg_file.commit()))
{
cellGem.error("Failed to save gem config to '%s' (error=%s)", cfg_name, fs::g_tls_error);
}
}

51
rpcs3/Emu/Io/gem_config.h Normal file
View File

@ -0,0 +1,51 @@
#pragma once
#include "Utilities/Config.h"
#include "pad_types.h"
#include <array>
enum class gem_btn
{
start,
select,
triangle,
circle,
cross,
square,
move,
t,
};
struct cfg_gem final : cfg::node
{
cfg_gem(node* owner, const std::string& name) : cfg::node(owner, name) {}
cfg::_enum<pad_button> start{ this, "Start", pad_button::start };
cfg::_enum<pad_button> select{ this, "Select", pad_button::select };
cfg::_enum<pad_button> triangle{ this, "Triangle", pad_button::triangle };
cfg::_enum<pad_button> circle{ this, "Circle", pad_button::circle };
cfg::_enum<pad_button> cross{ this, "Cross", pad_button::cross };
cfg::_enum<pad_button> square{ this, "Square", pad_button::square };
cfg::_enum<pad_button> move{ this, "Move", pad_button::R1 };
cfg::_enum<pad_button> t{ this, "T", pad_button::R2 };
std::map<u32, std::map<u32, gem_btn>> buttons;
std::optional<gem_btn> find_button(u32 offset, u32 keycode) const;
};
struct cfg_gems final : cfg::node
{
cfg_gem player1{ this, "Player 1" };
cfg_gem player2{ this, "Player 2" };
cfg_gem player3{ this, "Player 3" };
cfg_gem player4{ this, "Player 4" };
cfg_gem player5{ this, "Player 5" };
cfg_gem player6{ this, "Player 6" };
cfg_gem player7{ this, "Player 7" };
std::array<cfg_gem*, 7> players{ &player1, &player2, &player3, &player4, &player5, &player6, &player7 }; // Thanks gcc!
bool load();
void save() const;
};