Joystick C++ library
v2.0.5
Table of contents
- Overview
- Versions
- Library files
- Joystick class description
- Build and connect to your project
- Example
Overview
Joystick is a C++ library which assists developers in interfacing with various types of joysticks, all without relying on third-party dependencies. The library is compatible with Linux (uses Linux native joysticks interface) and Windows (uses WinAPI). The library doesn’t have third party dependencies. The library is a CMake project and utilizes C++17 standard.
Versions
Table 1 - Library versions.
Version | Release date | What’s new |
---|---|---|
1.0.0 | 27.11.2022 | - First version |
2.0.0 | 04.10.2023 | - Interface changed. - Class name changed from JoystickController to Joystick. - SDL2 library excluded. No more third-party dependencies. - Documentation updated. |
2.0.1 | 04.10.2023 | - Method description updated. |
2.0.2 | 15.10.2023 | - Documentation updated. - Files structure changed. - Variables names changed. |
2.0.3 | 15.04.2024 | - Documentation updated. |
2.0.4 | 17.05.2024 | - Documentation updated. |
2.0.5 | 18.07.2024 | - CMake structure updated. |
Library files
The library is supplied only by source code. The user is given a set of files in the form of a CMake project (repository). The repository structure is shown below:
CMakeLists.txt ------------ Main CMake file of the library.
src ----------------------- Folder with library source code.
CMakeLists.txt -------- CMake file of the library.
Joystick.h ------------ Main library header file.
JoystickVersion.h ----- Header file with library version.
JoystickVersion.h.in -- CMake service file to generate version header.
Joystick.cpp ---------- C++ implementation file.
test ---------------------- Folder for test application files.
CMakeLists.txt -------- CMake file for test application.
main.cpp -------------- Source C++ file of test application.
example ------------------- Folder for example application files.
CMakeLists.txt -------- CMake file for example application.
main.cpp -------------- Source C++ file of example application.
Joystick class description
Joystick class declaration
Joystick interface class declared in Joystick.h file. Class declaration:
namespace cr
{
namespace utils
{
/// Joystick class.
class Joystick
{
public:
/// Get Joystick class version.
static std::string getVersion();
/// Class constructor.
Joystick();
/// Class destructor.
~Joystick();
/// Find available joysticks.
std::vector<JoystickInfo> findJoysticks();
/// Open joystick.
bool openJoystick(int id);
/// Close joystick.
void closeJoystick();
/// Check status of a button.
bool getButtonState(int buttonId);
/// Get hat value.
int getHatValue();
/// Get axis value.
int getAxisValue(int axisId);
};
}
}
getVersion method
The getVersion() method returns string of current class version. Method declaration:
static std::string getVersion();
Method can be used without Joystick class instance:
std::cout << "Joystick class version: " << Joystick::getVersion();
Console output:
Joystick class version: 2.0.5
findJoysticks method
The findJoysticks() method detects connected joysticks and provides information about joysticks. When called, this method returns a vector of JoystickInfo structures, each containing properties of the detected joysticks. Method declaration:
std::vector<JoystickInfo> findJoysticks();
Returns: vector of JoystickInfo structures. JoystickInfo structure defined in Joystick.h file. Structure declaration:
/// Struct for joystick data.
struct JoystickInfo
{
/// Joystick name.
std::string name;
/// Joystick id (from 0).
int id;
/// Number of buttons.
int numButtons;
/// Number of axes.
int numAxes;
};
Table 2 - Joystick properties description.
Parameter | Description |
---|---|
name | Name of joystick. |
id | Joystick id from 0 to max number of connected joystick -1. |
numButtons | Number of available buttons. |
numAxes | Number of supported axes. |
openJoystick method
The openJoystick(…) method opens joystick which is specified by id. Method declaration:
bool openJoystick(int id);
Parameter | Value |
---|---|
id | joystick id from 0 to [number of joysticks - 1] connected joysticks which can be determined by length of vector returned by findJoystick() method. |
Returns: TRUE if it success or FALSE if not.
closeJoystick method
The closeJoystick() method closes an opened joystick. Method declaration:
void closeJoystick();
getButtonState method
The getButtonState(…) method serves the purpose of reading state of a button from a joystick. Method declaration:
bool getButtonState(int buttonId);
Parameter | Value |
---|---|
buttonId | Button id which can be from zero to number of buttons in JoystickInfo structure. |
Returns: TRUE if button is pressed or FALSE if not.
getHatValue method
The getHatValue() method is designated to read hat value from a joystick. Method declaration:
int getHatValue();
Returns: hat value from 0 to 8. Return values:
Value | hat position |
---|---|
0 | Not pressed |
1 | Up |
2 | Up and right |
3 | Right |
4 | Right and down |
5 | Down |
6 | Down and left |
7 | Left |
8 | Left and up |
getAxisValue method
The getAxisValue() method is designated to read axis value from a joystick. Method declaration:
int getAxisValue(int axisId);
Parameter | Value |
---|---|
axisId | Axix id which can be from 0 to [number of axis - 1] in JoystickInfo structure. |
Returns: Axis position. Range depends on joystick but generally between 32767 and -32767.
Build and connect to your project
Typical commands to build Joystick library:
cd Joystick
mkdir build
cd build
cmake ..
make
If you want connect Joystick library to your CMake project as source code you can make follow. For example, if your repository has structure:
CMakeLists.txt
src
CMakeList.txt
yourLib.h
yourLib.cpp
Create 3rdparty folder in your repository. Copy Joystick repository to 3rdparty folder. The new structure of your repository will be as follows:
CMakeLists.txt
src
CMakeList.txt
yourLib.h
yourLib.cpp
3rdparty
Joystick
Create CMakeLists.txt file in 3rdparty folder. CMakeLists.txt should contain:
cmake_minimum_required(VERSION 3.13)
################################################################################
## 3RD-PARTY
## dependencies for the project
################################################################################
project(3rdparty LANGUAGES CXX)
################################################################################
## SETTINGS
## basic 3rd-party settings before use
################################################################################
# To inherit the top-level architecture when the project is used as a submodule.
SET(PARENT ${PARENT}_YOUR_PROJECT_3RDPARTY)
# Disable self-overwriting of parameters inside included subdirectories.
SET(${PARENT}_SUBMODULE_CACHE_OVERWRITE OFF CACHE BOOL "" FORCE)
################################################################################
## CONFIGURATION
## 3rd-party submodules configuration
################################################################################
SET(${PARENT}_SUBMODULE_JOYSTICK ON CACHE BOOL "" FORCE)
if (${PARENT}_SUBMODULE_JOYSTICK)
SET(${PARENT}_JOYSTICK ON CACHE BOOL "" FORCE)
SET(${PARENT}_JOYSTICK_TEST OFF CACHE BOOL "" FORCE)
SET(${PARENT}_JOYSTICK_EXAMPLE OFF CACHE BOOL "" FORCE)
endif()
################################################################################
## INCLUDING SUBDIRECTORIES
## Adding subdirectories according to the 3rd-party configuration
################################################################################
if (${PARENT}_SUBMODULE_JOYSTICK)
add_subdirectory(Joystick)
endif()
File 3rdparty/CMakeLists.txt adds folder Joystick to your project and excludes test application and examples from compiling (by default test applications and example excluded from compiling if Joystick included as sub-repository). The new structure of your repository:
CMakeLists.txt
src
CMakeList.txt
yourLib.h
yourLib.cpp
3rdparty
CMakeLists.txt
Joystick
Next you need include folder 3rdparty in main CMakeLists.txt file of your repository. Add string at the end of your main CMakeLists.txt:
add_subdirectory(3rdparty)
Next you have to include Joystick library in your src/CMakeLists.txt file:
target_link_libraries(${PROJECT_NAME} Joystick)
Done!
Example
This example illustrates the open a joystick and read button values.
#include <iostream>
#include <thread>
#include <chrono>
#include "Joystick.h"
int main(void)
{
// Create joystick controller.
cr::utils::Joystick joyStickController;
// Read number of connected joysticks.
std::vector<cr::utils::JoystickInfo> joysticks;
joysticks = joyStickController.findJoysticks();
// Open first joystick
joyStickController.openJoystick(joysticks.at(0).id);
// Print joystick infos.
std::cout << "Joystick name : " << joysticks.at(0).name << std::endl;
std::cout << "Number of button : " << joysticks.at(0).numButtons << std::endl;
std::cout << "Number of axes : " << joysticks.at(0).numAxes << std::endl;
// Read all avaliable buttons one by one
while (true)
{
for (int i = 0; i < joysticks.at(0).numButtons; ++i)
{
if (joyStickController.getButtonState(i) == true)
std::cout << "Button : " << i << " pressed" << std::endl;
}
std::this_thread::sleep_for(std::chrono::milliseconds(100));
}
return 0;
}