| /* |
| * Copyright 2016 The Fuchsia Authors. All rights reserved. |
| * |
| * Redistribution and use in source and binary forms, with or without |
| * modification, are permitted provided that the following conditions |
| * are met: |
| * |
| * 1. Redistributions of source code must retain the above copyright |
| * notice, this list of conditions and the following disclaimer. |
| * 2. Redistributions in binary form must reproduce the above copyright |
| * notice, this list of conditions and the following disclaimer in the |
| * documentation and/or other materials provided with the distribution. |
| * |
| * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND |
| * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
| * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
| * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY |
| * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
| * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
| * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
| * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
| * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF |
| * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
| */ |
| |
| #pragma once |
| |
| #include <wtf/Noncopyable.h> |
| |
| #include <hid/hid.h> |
| |
| #include <future> |
| #include <map> |
| #include <string> |
| #include <vector> |
| |
| #include <zircon/types.h> |
| |
| namespace Fuchsia { |
| |
| #pragma mark - Event |
| |
| class Event { |
| public: |
| enum Type { |
| kMouse, |
| kKey |
| }; |
| |
| Type type() const { return fType; } |
| int eventSource() const { return fEventSource; } |
| |
| protected: |
| Event(Type type, int eventSource) |
| : fType(type) |
| , fEventSource(eventSource) |
| { |
| } |
| |
| virtual ~Event() {} |
| |
| private: |
| Type fType; |
| int fEventSource; |
| }; |
| |
| typedef std::shared_ptr<Event> EventPtr; |
| typedef std::vector<EventPtr> EventList; |
| |
| #pragma mark - MouseEvent |
| |
| class MouseEvent : public Event { |
| public: |
| MouseEvent(int fd, int x, int y, int buttons) |
| : Event(kMouse, fd) |
| , fDeltaX(x) |
| , fDeltaY(y) |
| , fButtons(buttons) |
| { |
| } |
| |
| int fDeltaX; |
| int fDeltaY; |
| int fButtons; |
| }; |
| |
| #pragma mark - KeyEvent |
| |
| class KeyEvent : public Event { |
| public: |
| KeyEvent(int fd, uint8_t keyCode, bool pressed) |
| : Event(kKey, fd) |
| , fKeyCode(keyCode) |
| , fPressed(pressed) |
| { |
| } |
| |
| uint8_t keycode() const { return fKeyCode; } |
| bool pressed() const { return fPressed; } |
| |
| private: |
| uint8_t fKeyCode; |
| bool fPressed; |
| }; |
| |
| #pragma mark - InputReportHandler |
| |
| |
| class InputReportHandler { |
| public: |
| ssize_t openHandle(); |
| |
| void checkForEvents(EventList&); |
| |
| int descriptor() const { return fDescriptor; } |
| zx_handle_t handle() const { return fHandle; } |
| |
| protected: |
| InputReportHandler(int descriptor, const std::string& deviceName); |
| virtual ~InputReportHandler(); |
| |
| virtual void handleReport(size_t byteLength, const char* reportData, EventList& events) = 0; |
| |
| int fDescriptor; |
| std::string fName; |
| zx_handle_t fHandle = { ZX_HANDLE_INVALID }; |
| }; |
| |
| typedef std::shared_ptr<InputReportHandler> InputReportHandlerPtr; |
| |
| class MouseReportHandler : public InputReportHandler { |
| public: |
| MouseReportHandler(int descriptor, const std::string& deviceName); |
| void handleReport(size_t byteLength, const char* reportData, EventList& events) override; |
| }; |
| |
| class KeyboardReportHandler : public InputReportHandler { |
| public: |
| KeyboardReportHandler(int descriptor, const std::string& deviceName); |
| void handleReport(size_t byteLength, const char* reportData, EventList& events) override; |
| |
| private: |
| hid_keys_t fKeyState = {}; |
| }; |
| |
| class InputHandler { |
| WTF_MAKE_NONCOPYABLE(InputHandler); |
| |
| public: |
| InputHandler(); |
| |
| void openDevices(); |
| |
| bool hasEvents(); |
| EventList getPendingEvents(); |
| void addEvents(const EventList& newEvents); |
| |
| private: |
| void startReaderThread(); |
| void readEvents(); |
| |
| std::vector<InputReportHandlerPtr> fReportHandlers; |
| EventList fEvents; |
| std::mutex fEventsMutex; |
| std::thread fEventReaderThread; |
| }; |
| |
| } |