blob: 74bc9ac72d54dc49631ccec646411d371ce56b52 (
plain) (
blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
|
// license:BSD-3-Clause
// copyright-holders:Aaron Giles
/***************************************************************************
natkeyboard.h
Natural keyboard input support.
***************************************************************************/
#pragma once
#ifndef EMU_NATKEYBOARD_H
#define EMU_NATKEYBOARD_H
//**************************************************************************
// TYPE DEFINITIONS
//**************************************************************************
// keyboard helper function delegates
typedef delegate<int (const char32_t *, size_t)> ioport_queue_chars_delegate;
typedef delegate<bool (char32_t)> ioport_accept_char_delegate;
typedef delegate<bool ()> ioport_charqueue_empty_delegate;
// ======================> natural_keyboard
// buffer to handle copy/paste/insert of keys
class natural_keyboard
{
DISABLE_COPYING(natural_keyboard);
public:
// construction/destruction
natural_keyboard(running_machine &machine);
// getters and queries
running_machine &machine() const { return m_machine; }
bool empty() const { return (m_bufbegin == m_bufend); }
bool full() const { return ((m_bufend + 1) % m_buffer.size()) == m_bufbegin; }
bool can_post() const { return (!m_queue_chars.isnull() || !m_keycode_map.empty()); }
bool is_posting() const { return (!empty() || (!m_charqueue_empty.isnull() && !m_charqueue_empty())); }
bool in_use() const { return m_in_use; }
// configuration
void configure(ioport_queue_chars_delegate queue_chars, ioport_accept_char_delegate accept_char, ioport_charqueue_empty_delegate charqueue_empty);
void set_in_use(bool usage);
// posting
void post(char32_t ch);
void post(const char32_t *text, size_t length = 0, const attotime &rate = attotime::zero);
void post_utf8(const char *text, size_t length = 0, const attotime &rate = attotime::zero);
void post_coded(const char *text, size_t length = 0, const attotime &rate = attotime::zero);
// debugging
std::string dump();
private:
// internal keyboard code information
struct keycode_map_entry
{
char32_t ch;
ioport_field * field[UCHAR_SHIFT_END + 1 - UCHAR_SHIFT_BEGIN];
};
// internal helpers
void build_codes(ioport_manager &manager);
bool can_post_directly(char32_t ch);
bool can_post_alternate(char32_t ch);
attotime choose_delay(char32_t ch);
void internal_post(char32_t ch);
void timer(void *ptr, int param);
std::string unicode_to_string(char32_t ch);
const keycode_map_entry *find_code(char32_t ch) const;
// internal state
running_machine & m_machine; // reference to our machine
bool m_in_use; // is natural keyboard in use?
u32 m_bufbegin; // index of starting character
u32 m_bufend; // index of ending character
std::vector<char32_t> m_buffer; // actual buffer
bool m_status_keydown; // current keydown status
bool m_last_cr; // was the last char a CR?
emu_timer * m_timer; // timer for posting characters
attotime m_current_rate; // current rate for posting
ioport_queue_chars_delegate m_queue_chars; // queue characters callback
ioport_accept_char_delegate m_accept_char; // accept character callback
ioport_charqueue_empty_delegate m_charqueue_empty; // character queue empty callback
std::vector<keycode_map_entry> m_keycode_map; // keycode map
};
#endif
|