Is it just a PC? What kind of performance can you expect out of something like this? Would MAME run games up to early 90s? Because if yes, $32 seems like the way to go...
April 23, 2024, 12:01:37 pm
PORT_BIT( 0x4000, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_TOGGLE PORT_NAME("Center Wheel Edge") /* center edge on steering wheel, IPT_ACTIVE_HIGH fixes the steering alignment in game! */
Wow! Well done Yolo, sounds like progress at last!! Can't wait to see the changes
PORT_BIT( 0x4000, IP_ACTIVE_HIGH, IPT_CUSTOM ) PORT_TOGGLE PORT_NAME("Center Wheel Edge") /* center edge on steering wheel, IPT_ACTIVE_HIGH fixes the steering alignment in game! */
#include <numeric> // For std::accumulate
// Function to calculate the Exponential Moving Average (EMA)
uint16_t harddriv_state::calculate_ema(uint16_t new_value) {
static float ema_wheel = 0.0; // Persistent storage of EMA across calls
static bool ema_initialized = false; // To check if ema_wheel is initialized
static const float alpha = 0.082; // Smoothing constant
if (!ema_initialized) {
ema_wheel = new_value; // Initialize EMA with the first raw value
ema_initialized = true;
} else {
ema_wheel = alpha * new_value + (1 - alpha) * ema_wheel;
}
// Ensure the last digit of the EMA output is always zero
return static_cast<uint16_t>(ema_wheel) & 0xFFF0;
}
// Main function to handle wheel input and apply adjustments
uint16_t harddriv_state::hdc68k_wheel_r() {
static const uint16_t g_latchpoint = 0x8000; // Center point for wheel edge detection
static bool initialized = false; // To ensure the initial setup is done only once
static int16_t last_offset = 0; // To store the last offset applied
static int wheel_edge_zero_count = 0; // Counter for how many times wheel edge has been set to 0
static int resets_recorded = 0; // Counter to delay offset recording
// Initial setup
if (!initialized) {
m_hdc68k_wheel_edge = 1; // Set the edge to 1 at the start of the game
initialized = true; // Prevent further initialization
}
uint16_t new_wheel_raw = m_12badc[0].read_safe(0xffff) << 4;
uint16_t ema_wheel = calculate_ema(new_wheel_raw) << 3;
// If the game has reset the wheel edge to 0, handle the deviation
if (m_hdc68k_wheel_edge == 0) {
wheel_edge_zero_count++; // Increment the counter each time wheel edge is 0
// Record adjustment only after the first reset is recorded
if (resets_recorded > 0) {
// Check for deviation from the center point
if (ema_wheel != g_latchpoint) {
int16_t adjustment = g_latchpoint - ema_wheel; // Calculate the necessary adjustment
ema_wheel += adjustment; // Correct the EMA to the center point
last_offset = adjustment; // Store the last offset applied
} else {
last_offset = 0; // No offset needed if already at center
}
}
resets_recorded++; // Increment resets recorded after processing
m_hdc68k_wheel_edge = 1; // Set the wheel edge back to 1 after handling the adjustment
}
// Debugging output
popmessage("Wheel Raw: %04X, EMA Wheel: %04X, Last Offset: %d, Edge: %d, Edge 0 Count: %d, Resets Recorded: %d",
new_wheel_raw, ema_wheel, last_offset, m_hdc68k_wheel_edge, wheel_edge_zero_count, resets_recorded);
return ema_wheel; // Use the adjusted EMA directly
}
// Handlers for the wheel and port inputs
m_maincpu->space(AS_PROGRAM).install_read_handler(0x400000, 0x400001, read16smo_delegate(*this, FUNC(harddriv_state::hdc68k_wheel_r)));
m_maincpu->space(AS_PROGRAM).install_write_handler(0x408000, 0x408001, write16smo_delegate(*this, FUNC(harddriv_state::hdc68k_wheel_edge_reset_w)));
m_maincpu->space(AS_PROGRAM).install_read_handler(0xa80000, 0xafffff, read16smo_delegate(*this, FUNC(harddriv_state::hda68k_port1_r)));
class harddriv_state : public device_t
{
public:
void reset_wheel_offset(); // Function to reset the wheel offset
harddriv_state(const machine_config &mconfig, device_type type, const char *tag, device_t *owner, uint32_t clock);
void driver_msp(machine_config &config);
@@ -98,8 +102,21 @@ class harddriv_state : public device_t
void video_int_write_line(int state);
void sound_int_write_line(int state);
//New method declarations for steering logic
uint16_t hdc68k_wheel_r(); // Ensure this is declared only once
uint16_t custom_steering_logic();
uint16_t original_steering_logic();
// Add your EMA function declaration here
uint16_t calculate_ema(uint16_t new_value); // Corrected declaration
protected:
int16_t wheel_offset = 0; // Make wheel_offset a member variable
void init_video();
INTERRUPT_GEN_MEMBER(hd68k_irq_gen);
TIMER_CALLBACK_MEMBER(deferred_adsp_bank_switch);
TIMER_CALLBACK_MEMBER(rddsp32_sync_cb);
@@ -122,7 +139,7 @@ class harddriv_state : public device_t
uint16_t hd68k_adc12_r();
uint16_t hdc68k_port1_r();
uint16_t hda68k_port1_r();
// uint16_t hdc68k_wheel_r();
uint16_t hd68k_sound_reset_r();
void hd68k_adc_control_w(offs_t offset, uint16_t data, uint16_t mem_mask = ~0);
Can I ask what game or emulator you are trying to get working that uses right click for off screen reload?Basically every game works with it. The number of games that don't have an off-screen function is less common, and right click is the standard, basically every gun I've seen sends a right click instead of left click if you click outside of screen boundaries. Only titles like Time Crisis that use a pedal instead don't really have off-screen support. The few titles I've tried so far with just a left click gun would just fire at the edge of the screen if I tried to off-screen reload, but maybe there are a few that see "is gun at border? Then reload" rather than relying on the gun to say "I can't see the screen, send right click instead".
I think using the Inject DLL code I have it would also be able to not just turn off the clicks from Vive Mouse but also intercept them and resend them. It is probably also possible to get the x,y mouse co-ords and then change whether it is left or right click. That should also remove the need for the python code.If something like that is possible it should be pretty useful.
If you have any problems compiling the Inject DLL code let me knowI used the pre-compiled version in the debug folders and it worked fine for disabling the vive buttons, with the exception of the menu button that still disables the cursor but that isn't really a big issue and I'm guessing it's hardcoded in vive mouse rather than something that's passed through and can be intercepted. With trigger, grip and trackpad that's still 3 usable buttons I can remap through OpenVR2Key because SteamVR still sees them fine.
Yeah, maybe you're right. Static calibration is fairly appealing, the problem is just everything else about the program is a bit half-baked and harder to get working than VD. I guess I could use OpenVR2Key and then something else to bind to mouse clicks. I'd also need to work out how to block Vive Mouse from receiving/sending keypresses like you did, seems like I need VS for the right dlls. Then I need to try and get AHK to intercept left clicks and turn them into right clicks if I'm clicking on the very edge of the screen for off-screen reloads. I also realised that vive mouse releases control of the mouse if you point it far enough off-screen, so I don't have to worry about wasting a button on it.
Keep it going Ond. I wanna see this thing finished in all it's glory!
This build needs a sticky thread