15#ifdef VRPN_USE_DEV_INPUT
16#include <sys/select.h>
21#include <linux/input.h>
30#define REPORT_ERROR(msg) { send_text_message(msg, timestamp, vrpn_TEXT_ERROR); }
32static const std::string EMPTY_STRING(
"");
34static std::string getDeviceNodes(
const std::string &device_name)
36 std::map<std::string, std::string> s_devicesNodes;
38 bool permission_missing =
false;
41 std::ostringstream oss;
42 oss <<
"/dev/input/event" << id;
44 int fd = open(oss.str().c_str(), O_RDONLY);
47 if((ioctl(fd, EVIOCGNAME(
sizeof(name)), name) >= 0)
48 && (s_devicesNodes.find(name) == s_devicesNodes.end())) {
49 s_devicesNodes[name] = oss.str();
54 if (errno == ENOENT)
break;
55 if (errno == EACCES) permission_missing =
true;
60 if (permission_missing) {
61 std::cout <<
"vrpn_DevInput device scan warning : permission denied for some nodes !" << std::endl;
64 std::map<std::string, std::string>::iterator node_name = s_devicesNodes.find(device_name);
65 if (node_name != s_devicesNodes.end()) {
66 return node_name->second;
74vrpn_DevInput::vrpn_DevInput(
const char* name,
vrpn_Connection * cxn,
const char *device_name,
const char * type,
int int_param )
77 , d_fileDescriptor(-1)
81 if (strcmp(type,
"keyboard") == 0) {
82 d_type = DEVICE_KEYBOARD;
83 }
else if (strcmp(type,
"absolute") == 0) {
84 d_type = DEVICE_MOUSE_ABSOLUTE;
85 }
else if (strcmp(type,
"relative") == 0) {
86 d_type = DEVICE_MOUSE_RELATIVE;
88 REPORT_ERROR(
"Third parameter must be keyboard, absolute or relative");
98 REPORT_ERROR(
"In case of keyboard, the value must be between 1 and 256");
103 case DEVICE_MOUSE_ABSOLUTE:
107 d_absolute_range = int_param;
109 case DEVICE_MOUSE_RELATIVE:
125 std::string node = getDeviceNodes(device_name);
126 if (node.length() == 0) {
128 sprintf(msg,
"vrpn_DevInput::vrpn_DevInput(): Could not get device %s",
134 d_fileDescriptor = open(node.c_str(), O_RDONLY);
135 if(d_fileDescriptor < 0){
137 sprintf(msg,
"vrpn_DevInput::vrpn_DevInput(): Could not open device %s (%s)",
138 device_name, strerror(errno));
146vrpn_DevInput::~vrpn_DevInput()
148 if (d_fileDescriptor >= 0) {
149 close(d_fileDescriptor);
151 d_fileDescriptor = -1;
156void vrpn_DevInput::mainloop()
167int vrpn_DevInput::get_report()
171 if (d_fileDescriptor < 0) {
176 FD_SET( d_fileDescriptor, &readset );
177 struct timeval timeout = { 0, 0 };
178 select( d_fileDescriptor+1, &readset, NULL, NULL, &timeout );
182 if( ! FD_ISSET( d_fileDescriptor, &readset ) )
185 struct input_event event;
186 if (read(d_fileDescriptor, &event,
sizeof(event)) <
sizeof(event)) {
190 switch (event.type) {
192 int button_number =
event.code;
193 if ((d_type == DEVICE_MOUSE_RELATIVE) || (d_type == DEVICE_MOUSE_ABSOLUTE)) {
194 button_number -= BTN_MOUSE;
197 buttons[button_number] =
event.value;
201 int channel_number =
event.code;
210 int channel_number =
event.code;
212 vrpn_float64 value = ((vrpn_float64)event.value - d_absolute_min) / d_absolute_range;
223void vrpn_DevInput::report_changes( vrpn_uint32 class_of_service )
234void vrpn_DevInput::report( vrpn_uint32 class_of_service )
vrpn_float64 last[vrpn_CHANNEL_MAX]
vrpn_float64 channel[vrpn_CHANNEL_MAX]
virtual void report(vrpn_uint32 class_of_service=vrpn_CONNECTION_LOW_LATENCY, const struct timeval time=vrpn_ANALOG_NOW)
Send a report whether something has changed or not (for servers) Optionally, tell what time to stamp ...
virtual void report_changes(vrpn_uint32 class_of_service=vrpn_CONNECTION_LOW_LATENCY, const struct timeval time=vrpn_ANALOG_NOW)
Send a report only if something has changed (for servers) Optionally, tell what time to stamp the val...
Generic connection class not specific to the transport mechanism.
#define REPORT_ERROR(msg)
#define vrpn_gettimeofday