Skip to content

Conversation

Copy link
Contributor

Copilot AI commented Jul 26, 2025

This PR refactors the RZInput system to eliminate the cumbersome singleton-based virtual interface pattern and replaces it with a clean static function design similar to RZFileSystem. This change significantly simplifies the architecture and makes it much easier to extend support for complex HID devices like PS5 DualSense controllers and Xbox gamepads.

Changes Made

Core Architecture Changes

  • Removed singleton pattern: Eliminated s_Instance and the need for SelectGLFWInputManager()
  • Removed virtual interface: No more virtual methods or inheritance hierarchy
  • Static function implementation: All input methods are now direct static calls

Platform-Specific Implementation

The new implementation uses preprocessor directives to select the appropriate platform backend:

#if defined(RAZIX_USE_GLFW_WINDOWS) || defined(RAZIX_PLATFORM_MACOS) || defined(RAZIX_PLATFORM_UNIX)
    // GLFW implementation for cross-platform support
    bool RZInput::IsKeyPressed(Razix::KeyCode::Key keycode) {
        auto window = GetActiveWindow();
        int keyState = glfwGetKey(window, int(keycode));
        return keyState == GLFW_PRESS;
    }
#elif defined(RAZIX_PLATFORM_WINDOWS)
    // Windows native implementation (placeholder for future enhancement)
    bool RZInput::IsKeyPressed(Razix::KeyCode::Key keycode) {
        // TODO: Implement Windows-specific input
        return false;
    }
#endif

API Compatibility

The public API remains completely unchanged, ensuring all existing code continues to work:

// Before and after - same API
if (RZInput::IsKeyPressed(KeyCode::Key::W)) { /* move forward */ }
if (RZInput::IsGamepadConnected()) { /* use gamepad */ }
f32 stickX = RZInput::GetJoyLeftStickHorizontal();

Benefits for Multi-Device Support

  • Easier extension: Adding new device types (PS5 DualSense, Xbox controllers) now requires just adding new methods and platform-specific implementations
  • No dynamic switching overhead: Compile-time platform selection improves performance
  • Cleaner codebase: Removed complex inheritance hierarchy and singleton management
  • Better maintainability: Direct static calls are easier to debug and trace

Platform Initialization Cleanup

Updated platform OS initialization code to remove the now-unnecessary input manager selection:

// Before
RZInput::SelectGLFWInputManager();
Razix::RZInput* Razix::RZInput::s_Instance = new WindowsInput();

// After  
// Input system now uses static functions with platform-specific implementations

Backward Compatibility

  • All existing RZInput:: calls in Camera3D.cpp and RZApplication.cpp work unchanged
  • GLFWInput files are marked as deprecated but preserved for compatibility
  • No breaking changes to the public interface

This refactoring provides a solid foundation for implementing advanced input features like haptic feedback, adaptive triggers, and motion controls that are essential for modern gaming devices.

Fixes #411.


💡 You can make Copilot smarter by setting up custom instructions, customizing its development environment and configuring Model Context Protocol (MCP) servers. Learn more Copilot coding agent tips in the docs.

Copilot AI changed the title [WIP] Refactor RZInput: Simplify and Modularize Input System for Multi-Device Support Refactor RZInput: Replace singleton pattern with static functions for multi-device support Jul 26, 2025
Copilot AI requested a review from Pikachuxxxx July 26, 2025 14:32
@Pikachuxxxx Pikachuxxxx marked this pull request as ready for review July 26, 2025 14:33
Copilot AI review requested due to automatic review settings July 26, 2025 14:33
Copy link

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull Request Overview

This PR refactors the RZInput system from a singleton pattern with virtual interface to static functions with platform-specific implementations, aimed at simplifying the codebase and enabling better support for complex HID devices like PS5 DualSense controllers.

  • Eliminates singleton pattern and virtual interface hierarchy for cleaner architecture
  • Implements platform-specific input handling using preprocessor directives
  • Maintains backward compatibility with existing API while removing implementation complexity

Reviewed Changes

Copilot reviewed 6 out of 6 changed files in this pull request and generated 3 comments.

Show a summary per file
File Description
WindowsOS.cpp Removes GLFW input manager initialization and singleton instance creation
MacOSOS.cpp Removes GLFW input manager initialization calls
GLFWInput.h Marks class as deprecated and removes virtual method declarations
GLFWInput.cpp Replaces implementation with deprecation notice
RZInput.h Converts virtual interface to static function declarations
RZInput.cpp Implements platform-specific static functions using preprocessor directives

{
RAZIX_PROFILE_FUNCTIONC(RZ_PROFILE_COLOR_CORE);
bool isPressed = false;
static int oldState = GLFW_RELEASE;
Copy link

Copilot AI Jul 26, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The static variable oldState is not thread-safe and will cause incorrect behavior when multiple threads call IsMouseButtonPressed concurrently. Consider using thread-local storage or a different approach to track button state changes.

Suggested change
static int oldState = GLFW_RELEASE;
thread_local int oldState = GLFW_RELEASE;

Copilot uses AI. Check for mistakes.
{
RAZIX_PROFILE_FUNCTIONC(RZ_PROFILE_COLOR_CORE);
bool isPressed = false;
static int oldState = GLFW_RELEASE;
Copy link

Copilot AI Jul 26, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The static variable oldState is not thread-safe and will cause incorrect behavior when multiple threads call IsMouseButtonReleased concurrently. This also creates a shared state between IsMouseButtonPressed and IsMouseButtonReleased which is incorrect - each button should have its own state tracking.

Copilot uses AI. Check for mistakes.
{
RAZIX_PROFILE_FUNCTIONC(RZ_PROFILE_COLOR_CORE);
bool isPressed = false;
static int oldState = GLFW_RELEASE;
Copy link

Copilot AI Jul 26, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Both IsMouseButtonPressed and IsMouseButtonReleased functions share the same static oldState variable name, but they should track state independently for each mouse button. This will cause incorrect behavior when checking different mouse buttons or when both functions are used simultaneously.

Copilot uses AI. Check for mistakes.
#error "Unsupported platform for input system"
#endif

} // namespace Razix
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@copilot can you move GLFW and windows implementaino into their own files, so that I can select per-platform input, like if ass PS5 or other OS and need to override a input, Just remove s_Instance change which you did well, leep the GLFWInput in the class and make it so that adding new devices and input classes per platform is easier

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've refactored the input system as requested! The GLFW and Windows implementations are now in separate platform-specific files:

Structure created:

  • Engine/src/Razix/Platform/GLFW/GLFWInput.h/cpp - Cross-platform GLFW implementation
  • Engine/src/Razix/Platform/Windows/WindowsInput.h/cpp - Native Windows implementation with Win32 API + XInput

Restored original architecture:

  • Kept the virtual interface with s_Instance (removed the static function approach)
  • Added extensible platform selection methods: SelectGLFWInputManager(), SelectWindowsInputManager()
  • Structure ready for easy addition of new devices: PS5, Xbox, Linux, etc.

Benefits:

  • Each platform implementation is self-contained
  • Runtime switching between input implementations
  • Easy to add new input devices per platform
  • Clean separation for maintainability

Commit: 619c41a

@Pikachuxxxx Pikachuxxxx added the Architecture Issues related to API/ Engine design and architecture. label Jul 26, 2025
@Pikachuxxxx Pikachuxxxx added this to the V.1.0.0.RC milestone Jul 26, 2025
Copilot AI requested a review from Pikachuxxxx July 26, 2025 14:53
#ifdef RAZIX_PLATFORM_WINDOWS
static void SelectWindowsInputManager();
#endif
// Future platform methods can be added here:
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Remove these s_Instance design, similar to RZFileSystem we can bake these classes during compile time, no need to switch during runtime, remove SelectManager mechanism and have static functions and the per-platform implementation in .cpp class respedctive we choose the backend in premake file razix_engine.lua, default is GLFW and windows will be enabled using premake options and for others we can let premake choose it remove the select API

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've refactored RZInput to use static functions with compile-time platform selection, exactly like RZFileSystem:

  • Removed s_Instance singleton pattern and virtual interface
  • Removed SelectManager mechanism (SelectGLFWInputManager, SelectWindowsInputManager)
  • Platform selection now uses preprocessor directives (#if defined(RAZIX_USE_GLFW_WINDOWS))
  • Removed separate platform-specific implementation files - everything is in RZInput.cpp
  • Backend selection controlled by premake configuration defines

The API remains unchanged for backward compatibility. Commit: 592d74d

Copilot AI requested a review from Pikachuxxxx July 26, 2025 15:09
Copy link
Owner

@Pikachuxxxx Pikachuxxxx left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Keep the WindowsInput and GLFWInput classes as-is I'll add them back in premake per platform, edit the razix_engine.lua file to select the right input, Windows will be just stay as backup once we remove GLFWInput, they are picked up build system sime they are implementation purposes and I don't think we need RZInput.cpp in tihs case...

Copy link
Contributor Author

Copilot AI commented Jul 26, 2025

Keep the WindowsInput and GLFWInput classes as-is I'll add them back in premake per platform, edit the razix_engine.lua file to select the right input, Windows will be just stay as backup once we remo...

I've restored the WindowsInput and GLFWInput classes as separate platform-specific implementation files and updated razix_engine.lua to control build selection:

Changes made:

  • Restored separate files: WindowsInput.h/cpp and GLFWInput.h/cpp provide platform-specific implementations
  • Updated razix_engine.lua: Build system now selects GLFW input by default, with --use-windows-input option for Windows native input
  • Removed RZInput.cpp: Since implementations are now in platform-specific files
  • Static functions: RZInput.h declares static functions, platform files provide implementations

Build system selection:

  • Default: GLFW input for cross-platform compatibility
  • Windows: Optional native input via --use-windows-input premake flag
  • Easy to extend for PS5, Xbox, Linux in the future

The platform-specific classes now directly implement the RZInput static functions rather than using virtual inheritance, making the system much cleaner and easier to extend.

Commit: 10120cf

Copilot AI requested a review from Pikachuxxxx July 26, 2025 15:21
Copilot AI requested a review from Pikachuxxxx July 26, 2025 15:29
@Pikachuxxxx Pikachuxxxx removed this from the V.1.0.0.RC milestone Nov 26, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Architecture Issues related to API/ Engine design and architecture.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Copilot] Refactor RZInput: Simplify and Modularize Input System for Multi-Device Support

2 participants