reactjs-virtual-keyboard 1.0.2 → 2.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,18 +1,21 @@
1
1
  # reactjs-virtual-keyboard
2
2
 
3
- A customizable virtual keyboard component for React applications. Features multiple keyboard layouts (QWERTY, symbols, numbers), hardware keyboard synchronization, touch device support, and full TypeScript support.
3
+ A lightweight, customizable virtual keyboard component for React applications. Features multiple layouts, multi-language support, hardware keyboard sync, extensive customization options, and full TypeScript support.
4
4
 
5
- ## Features
5
+ 📚 **[Documentation & Live Demo](https://kalpesh442266.github.io/virtual-keyboard-lib/)**
6
6
 
7
- - **Multiple Layouts**: QWERTY letters, symbols, and numeric keypad layouts
8
- - **Hardware Keyboard Sync**: Virtual keyboard state syncs with physical keyboard (e.g., Caps Lock)
9
- - **Touch Optimized**: Designed for touch screens with continuous press support (hold backspace to delete)
10
- - **Customizable Themes**: CSS variables for easy theming, plus built-in theme classes
11
- - **TypeScript Support**: Full type definitions included
12
- - **Accessible**: Keyboard navigation and focus management
13
- - **Lightweight**: No external dependencies except React
7
+ ## âœĻ Features
14
8
 
15
- ## Installation
9
+ - **ðŸŽđ Multiple Layouts**: QWERTY letters, symbols, and numeric keypad
10
+ - **🌍 Multi-Language Support**: Built-in language switcher with custom language layouts
11
+ - **âŒĻïļ Hardware Keyboard Sync**: Virtual keyboard syncs with physical keyboard (Caps Lock, key presses)
12
+ - **ðŸ“ą Touch Optimized**: Continuous press support (hold backspace to delete)
13
+ - **ðŸŽĻ Highly Customizable**: Custom layouts, key labels, disabled/hidden keys, render functions
14
+ - **ðŸŠķ Lightweight**: Only ~26 KB minified (~6.3 KB gzipped), no external dependencies
15
+ - **📘 TypeScript**: Full type definitions included
16
+ - **â™ŋ Accessible**: Keyboard navigation and focus management
17
+
18
+ ## ðŸ“Ķ Installation
16
19
 
17
20
  ```bash
18
21
  npm install reactjs-virtual-keyboard
@@ -22,11 +25,11 @@ yarn add reactjs-virtual-keyboard
22
25
  pnpm add reactjs-virtual-keyboard
23
26
  ```
24
27
 
25
- ## Quick Start
28
+ ## 🚀 Quick Start
26
29
 
27
- ### Option 1: GlobalVirtualKeyboard (Easiest)
30
+ ### Option 1: GlobalVirtualKeyboard (Recommended)
28
31
 
29
- Add once at your app root - automatically shows keyboard when any input is focused:
32
+ Add once at your app root - automatically shows keyboard for all inputs:
30
33
 
31
34
  ```tsx
32
35
  import { GlobalVirtualKeyboard } from 'reactjs-virtual-keyboard';
@@ -35,11 +38,10 @@ import 'reactjs-virtual-keyboard/styles.css';
35
38
  function App() {
36
39
  return (
37
40
  <div>
38
- <input type="text" placeholder="Click me!" />
39
- <input type="email" placeholder="Email input" />
40
- <input type="number" placeholder="Number input" />
41
+ <input type="text" placeholder="Click any input!" />
42
+ <input type="email" placeholder="Email" />
43
+ <input type="number" placeholder="Numbers" />
41
44
 
42
- {/* Add once - works for all inputs */}
43
45
  <GlobalVirtualKeyboard />
44
46
  </div>
45
47
  );
@@ -48,7 +50,7 @@ function App() {
48
50
 
49
51
  ### Option 2: VirtualKeyboard (Manual Control)
50
52
 
51
- For more control over when the keyboard appears:
53
+ For more control over when and where the keyboard appears:
52
54
 
53
55
  ```tsx
54
56
  import { useRef, useState } from 'react';
@@ -58,27 +60,20 @@ import 'reactjs-virtual-keyboard/styles.css';
58
60
  function App() {
59
61
  const inputRef = useRef<HTMLInputElement>(null);
60
62
  const [isInputFocused, setIsInputFocused] = useState(false);
61
- const [value, setValue] = useState('');
62
63
 
63
64
  return (
64
65
  <div>
65
66
  <input
66
67
  ref={inputRef}
67
68
  type="text"
68
- value={value}
69
- onChange={(e) => setValue(e.target.value)}
70
69
  onFocus={() => setIsInputFocused(true)}
71
70
  onBlur={() => setIsInputFocused(false)}
72
- placeholder="Click to show keyboard"
73
71
  />
74
72
 
75
73
  {isInputFocused && (
76
74
  <VirtualKeyboard
77
75
  focusedInputRef={inputRef}
78
76
  isInputFocused={isInputFocused}
79
- inputType="text"
80
- onEnterClick={() => console.log('Enter pressed!')}
81
- onChange={(newValue) => setValue(newValue)}
82
77
  />
83
78
  )}
84
79
  </div>
@@ -86,242 +81,351 @@ function App() {
86
81
  }
87
82
  ```
88
83
 
89
- ## Components
84
+ ## 📖 API Reference
85
+
86
+ ### `<GlobalVirtualKeyboard />`
90
87
 
91
- ### GlobalVirtualKeyboard
88
+ Automatically manages keyboard visibility for all inputs on the page.
92
89
 
93
- Automatically shows keyboard when any text input is focused. Best for most use cases.
90
+ ```tsx
91
+ interface GlobalVirtualKeyboardProps {
92
+ enabled?: boolean; // Enable/disable keyboard (default: true)
93
+ className?: string; // Custom CSS class
94
+ onVisibilityChange?: (visible: boolean) => void; // Visibility change callback
95
+ onEnterClick?: () => void; // Enter key callback
96
+ onChange?: (value: string) => void; // Value change callback
97
+ }
98
+ ```
94
99
 
100
+ **Example:**
95
101
  ```tsx
96
102
  <GlobalVirtualKeyboard
97
- enabled={true} // Enable/disable the keyboard
98
- className="my-theme" // Custom CSS class
99
- onVisibilityChange={(visible) => {}} // Called when keyboard shows/hides
100
- onEnterClick={() => {}} // Called when Enter is pressed
101
- onChange={(value) => {}} // Called when value changes
103
+ enabled={true}
104
+ onEnterClick={() => console.log('Enter pressed!')}
105
+ onChange={(value) => console.log('Value:', value)}
102
106
  />
103
107
  ```
104
108
 
105
- | Prop | Type | Default | Description |
106
- |------|------|---------|-------------|
107
- | `enabled` | `boolean` | `true` | Enable/disable the keyboard |
108
- | `className` | `string` | - | Additional CSS class name |
109
- | `onVisibilityChange` | `(isVisible: boolean) => void` | - | Callback when visibility changes |
110
- | `onEnterClick` | `() => void` | - | Callback when Enter key is pressed |
111
- | `onChange` | `(value: string) => void` | - | Callback when value changes |
112
-
113
- ### VirtualKeyboard
114
-
115
- Manual control over keyboard display. Use when you need precise control.
116
-
117
- | Prop | Type | Default | Description |
118
- |------|------|---------|-------------|
119
- | `focusedInputRef` | `RefObject<HTMLInputElement \| HTMLTextAreaElement>` | **required** | Ref to the currently focused input element |
120
- | `isInputFocused` | `boolean` | **required** | Whether an input is currently focused |
121
- | `inputType` | `HTMLInputTypeAttribute` | `'text'` | Type of input (affects layout and validation) |
122
- | `onEnterClick` | `() => void` | - | Callback when Enter key is pressed |
123
- | `onChange` | `(value: string) => void` | - | Callback when value changes |
124
- | `className` | `string` | - | Additional CSS class name |
125
- | `defaultLayout` | `'letters' \| 'symbols' \| 'numbers'` | `'letters'` | Default keyboard layout |
126
- | `validate` | `(value: string) => boolean` | - | Custom validation function |
127
-
128
- ## Input Type Behaviors
109
+ ---
129
110
 
130
- The keyboard automatically adapts based on `inputType`:
111
+ ### `<VirtualKeyboard />`
131
112
 
132
- - **`text`**: Shows QWERTY layout, allows all characters
133
- - **`email`**: Shows QWERTY layout with quick access `.` and `@` keys
134
- - **`number`**: Shows numeric keypad, only allows digits
135
- - **`tel`**: Shows QWERTY layout, validates phone characters
136
- - **`password`**: Shows QWERTY layout, allows all characters
137
- - **`url`**: Shows QWERTY layout, validates URL characters
113
+ Main keyboard component with extensive customization options.
138
114
 
139
- ## Theming
140
-
141
- ### Using CSS Variables
142
-
143
- ```css
144
- :root {
145
- --vk-bg-color: #1a1a1a;
146
- --vk-key-color: #444444;
147
- --vk-key-text-color: #ffffff;
148
- --vk-key-active-color: #666666;
149
- --vk-key-hover-color: #555555;
150
- --vk-active-state-color: #4a90e2;
151
- --vk-key-border-radius: 0.5vw;
152
- --vk-key-font-size: 32px;
153
- --vk-gap: 0.75vw;
154
- --vk-padding: 1vw;
155
- --vk-height: 35vh;
156
- --vk-z-index: 2001;
115
+ ```tsx
116
+ interface VirtualKeyboardProps {
117
+ // Required props
118
+ focusedInputRef: RefObject<HTMLInputElement | HTMLTextAreaElement | null>;
119
+ isInputFocused: boolean;
120
+
121
+ // Layout & behavior
122
+ inputType?: 'text' | 'email' | 'number' | etc; // HTML input type
123
+ defaultLayout?: 'letters' | 'symbols' | 'numbers';
124
+ syncWithHardwareKeyboard?: boolean; // Enable hardware sync (default: true)
125
+
126
+ // Callbacks
127
+ onEnterClick?: () => void;
128
+ onChange?: (value: string) => void;
129
+ validate?: (value: string) => boolean; // Custom validation
130
+
131
+ // Customization
132
+ className?: string;
133
+ theme?: VirtualKeyboardTheme;
134
+ customLayouts?: {
135
+ letters?: string[][];
136
+ symbols?: string[][];
137
+ numbers?: string[][];
138
+ };
139
+
140
+ // Key customization
141
+ keyLabels?: Record<string, string>; // Custom key labels
142
+ hiddenKeys?: string[]; // Keys to hide
143
+ disabledKeys?: string[]; // Keys to disable
144
+ renderKey?: (key: string, defaultRender: ReactNode) => ReactNode;
145
+ renderSpecialKey?: (type: string, defaultRender: ReactNode) => ReactNode;
146
+
147
+ // Behavior configuration
148
+ continuousPressConfig?: {
149
+ initialDelay?: number; // Default: 500ms
150
+ interval?: number; // Default: 50ms
151
+ };
152
+ scrollConfig?: {
153
+ enabled?: boolean;
154
+ offset?: number;
155
+ };
157
156
  }
158
157
  ```
159
158
 
160
- ### Built-in Theme Classes
161
-
159
+ **Example with customization:**
162
160
  ```tsx
163
161
  <VirtualKeyboard
164
- className="vk-container--light" // Light theme
165
- // or
166
- className="vk-container--blue" // Blue theme
167
- // or
168
- className="vk-container--purple" // Purple theme
169
- {...props}
162
+ focusedInputRef={inputRef}
163
+ isInputFocused={isInputFocused}
164
+
165
+ // Custom key labels
166
+ keyLabels={{
167
+ enter: 'Submit',
168
+ space: 'Space Bar',
169
+ backspace: 'Del'
170
+ }}
171
+
172
+ // Hide specific keys
173
+ hiddenKeys={['capslock']}
174
+
175
+ // Disable certain keys
176
+ disabledKeys={['@', '#']}
177
+
178
+ // Custom layout
179
+ customLayouts={{
180
+ letters: [
181
+ ['q', 'w', 'e', 'r', 't', 'y'],
182
+ ['a', 's', 'd', 'f', 'g', 'h'],
183
+ ['z', 'x', 'c', 'v', 'b', 'n']
184
+ ]
185
+ }}
186
+
187
+ // Adjust continuous press behavior
188
+ continuousPressConfig={{
189
+ initialDelay: 300,
190
+ interval: 40
191
+ }}
192
+
193
+ // Disable hardware keyboard sync
194
+ syncWithHardwareKeyboard={false}
170
195
  />
171
196
  ```
172
197
 
173
- ### Custom Theme Example
198
+ ---
199
+
200
+ ## ðŸŽĻ Theming
201
+
202
+ ### Using CSS Variables
174
203
 
175
204
  ```css
176
- .my-custom-theme {
177
- --vk-bg-color: #2d3748;
178
- --vk-key-color: #4a5568;
179
- --vk-key-text-color: #e2e8f0;
180
- --vk-key-hover-color: #718096;
181
- --vk-key-active-color: #a0aec0;
182
- --vk-active-state-color: #48bb78;
205
+ .vk-container {
206
+ --vk-bg-color: #2c3e50;
207
+ --vk-key-color: #34495e;
208
+ --vk-key-text-color: #ecf0f1;
209
+ --vk-key-active-color: #3498db;
210
+ --vk-key-hover-color: #2c3e50;
211
+ --vk-active-state-color: #e74c3c;
212
+ --vk-key-border-radius: 8px;
213
+ --vk-key-font-size: 18px;
214
+ --vk-key-height: 50px;
183
215
  }
184
216
  ```
185
217
 
186
- ## Hooks
218
+ ### Theme Object
187
219
 
188
- ### useCaretManager
220
+ ```tsx
221
+ const darkTheme = {
222
+ backgroundColor: '#1a1a1a',
223
+ keyColor: '#2d2d2d',
224
+ keyTextColor: '#ffffff',
225
+ keyActiveColor: '#0066cc',
226
+ keyHoverColor: '#3d3d3d',
227
+ activeStateColor: '#00cc66',
228
+ keyBorderRadius: '6px',
229
+ keyFontSize: '16px',
230
+ keyHeight: '48px'
231
+ };
232
+
233
+ <VirtualKeyboard theme={darkTheme} {...props} />
234
+ ```
189
235
 
190
- Manages caret position and text insertion/deletion:
236
+ ---
191
237
 
192
- ```tsx
193
- import { useCaretManager } from 'reactjs-virtual-keyboard';
238
+ ## 🔧 Utility Functions & Hooks
194
239
 
195
- function CustomKeyboard() {
196
- const inputRef = useRef<HTMLInputElement>(null);
197
- const { insertText, backspace } = useCaretManager(inputRef);
240
+ For advanced use cases, you can import utilities directly:
198
241
 
199
- return (
200
- <button onClick={() => insertText('Hello')}>Insert Text</button>
201
- <button onClick={backspace}>Delete</button>
202
- );
203
- }
242
+ ```tsx
243
+ import {
244
+ // Caret management
245
+ createCaretManager,
246
+
247
+ // Hardware keyboard event handling
248
+ setupHardwareKeyboard,
249
+
250
+ // Validation utilities
251
+ validateValueUtil,
252
+ getInitialLayout,
253
+
254
+ // Scroll utilities
255
+ scrollInputIntoView,
256
+ resetScrollPosition,
257
+
258
+ // Input value sync
259
+ setInputValueAndDispatchEvents,
260
+
261
+ // Hooks (only for React state/effects)
262
+ useContinuousPress,
263
+ useKeyboardScroll
264
+ } from 'reactjs-virtual-keyboard';
204
265
  ```
205
266
 
206
- ### useContinuousPress
267
+ ### `createCaretManager`
207
268
 
208
- Handle hold-to-repeat functionality:
269
+ Pure function for managing caret position and text manipulation:
209
270
 
210
271
  ```tsx
211
- import { useContinuousPress } from 'reactjs-virtual-keyboard';
272
+ import { createCaretManager } from 'reactjs-virtual-keyboard';
212
273
 
213
- function DeleteButton({ onDelete }) {
214
- const handlers = useContinuousPress(onDelete, {
215
- initialDelay: 500, // Start repeating after 500ms
216
- interval: 50, // Repeat every 50ms
217
- });
274
+ const inputRef = useRef<HTMLInputElement>(null);
275
+ const { insertText, backspace } = createCaretManager(() => inputRef.current);
218
276
 
219
- return <button {...handlers}>Delete</button>;
220
- }
277
+ // Insert text at caret position
278
+ insertText('Hello');
279
+
280
+ // Delete character before caret
281
+ backspace();
221
282
  ```
222
283
 
223
- ### useHardwareKeyboard
284
+ ### `setupHardwareKeyboard`
224
285
 
225
- Sync with physical keyboard events:
286
+ Set up hardware keyboard event listeners:
226
287
 
227
288
  ```tsx
228
- import { useHardwareKeyboard } from 'reactjs-virtual-keyboard';
289
+ import { setupHardwareKeyboard } from 'reactjs-virtual-keyboard';
229
290
 
230
- function KeyboardHandler() {
231
- useHardwareKeyboard({
232
- isInputFocused: true,
291
+ useEffect(() => {
292
+ const cleanup = setupHardwareKeyboard({
233
293
  onBackspace: () => console.log('Backspace'),
234
294
  onEnter: () => console.log('Enter'),
235
295
  onSpace: () => console.log('Space'),
236
- onCapsToggle: () => console.log('Caps Lock'),
237
- onKeyClick: (key) => console.log('Key:', key),
296
+ onCapsToggle: () => console.log('Caps'),
297
+ onKeyClick: (key) => console.log('Key:', key)
238
298
  });
239
- }
299
+
300
+ return cleanup; // Clean up listeners
301
+ }, []);
240
302
  ```
241
303
 
242
- ### useKeyboardScroll
304
+ ---
305
+
306
+ ## ðŸ“ą Input Type Behaviors
307
+
308
+ The keyboard automatically adapts to different input types:
309
+
310
+ | Input Type | Layout | Special Keys | Validation |
311
+ |-----------|--------|--------------|------------|
312
+ | `text` | QWERTY | All | None |
313
+ | `email` | QWERTY + @ | Space, @ | Email chars only |
314
+ | `number` | Numbers only | Backspace, Enter | Digits only |
315
+ | `tel` | Numbers | Phone chars | Digits, +, - |
316
+ | `url` | QWERTY | .com, www. | URL chars |
243
317
 
244
- Automatically scroll inputs into view when keyboard appears:
318
+ ---
319
+
320
+ ## ðŸŽŊ Custom Layouts Example
245
321
 
246
322
  ```tsx
247
- import { useKeyboardScroll } from 'reactjs-virtual-keyboard';
323
+ const customLayouts = {
324
+ letters: [
325
+ ['a', 'b', 'c', 'd', 'e'],
326
+ ['f', 'g', 'h', 'i', 'j'],
327
+ ['k', 'l', 'm', 'n', 'o'],
328
+ ['p', 'q', 'r', 's', 't'],
329
+ ['u', 'v', 'w', 'x', 'y', 'z']
330
+ ],
331
+ symbols: [
332
+ ['!', '@', '#', '$', '%'],
333
+ ['^', '&', '*', '(', ')'],
334
+ ['-', '_', '=', '+', '['],
335
+ [']', '{', '}', '|', '\\']
336
+ ]
337
+ };
248
338
 
249
- function MyComponent() {
250
- const { scrollInput, resetScroll } = useKeyboardScroll();
339
+ <VirtualKeyboard
340
+ {...props}
341
+ customLayouts={customLayouts}
342
+ />
343
+ ```
251
344
 
252
- const handleFocus = (e: FocusEvent) => {
253
- const input = e.target as HTMLInputElement;
254
- scrollInput(input); // Shifts content up if input would be covered
255
- };
345
+ ---
256
346
 
257
- const handleBlur = () => {
258
- resetScroll(); // Restores original position
259
- };
347
+ ## 🎭 Custom Render Functions
260
348
 
261
- return <input onFocus={handleFocus} onBlur={handleBlur} />;
262
- }
349
+ ```tsx
350
+ <VirtualKeyboard
351
+ {...props}
352
+ renderKey={(key, defaultRender) => (
353
+ <div className="my-custom-key">
354
+ {key.toUpperCase()}
355
+ </div>
356
+ )}
357
+ renderSpecialKey={(type, defaultRender) => {
358
+ if (type === 'enter') {
359
+ return <button className="submit-btn">Submit</button>;
360
+ }
361
+ return defaultRender;
362
+ }}
363
+ />
263
364
  ```
264
365
 
265
- The hook automatically:
266
- - Calculates if the input would be covered by the keyboard
267
- - Smoothly transitions content up to keep input visible
268
- - Resets position when keyboard hides
269
- - Cleans up on component unmount
366
+ ---
270
367
 
271
- ## Custom Layouts
368
+ ## ðŸ“Ķ Bundle Size
272
369
 
273
- You can use the individual layout components:
370
+ - **ESM**: 26.14 kB minified (6.28 kB gzipped)
371
+ - **CJS**: 12.56 kB minified (4.69 kB gzipped)
372
+ - **CSS**: 6.03 kB (1.68 kB gzipped)
274
373
 
275
- ```tsx
276
- import {
277
- KeyboardLayout,
278
- TextLayout,
279
- NumbersLayout,
280
- QWERTY_LAYOUT,
281
- SYMBOLS_LAYOUT,
282
- NUMBERS_LAYOUT,
283
- } from 'reactjs-virtual-keyboard';
374
+ Tree-shaking enabled - import only what you need!
284
375
 
285
- // Use predefined layouts or create custom ones
286
- const CUSTOM_LAYOUT = [
287
- ['A', 'B', 'C'],
288
- ['D', 'E', 'F'],
289
- ['G', 'H', 'I'],
290
- ];
291
- ```
376
+ ---
292
377
 
293
- ## Accessibility
378
+ ## 🌐 Browser Support
294
379
 
295
- The keyboard includes:
380
+ - **Modern Browsers**: Chrome, Firefox, Safari, Edge (last 2 versions)
381
+ - **Mobile**: iOS Safari, Chrome Mobile, Samsung Internet
382
+ - Requires React 16.8+ (hooks support)
296
383
 
297
- - Focus management to prevent input blur when clicking keys
298
- - `aria-label` attributes on special keys
299
- - Keyboard navigation support
300
- - Respects `prefers-reduced-motion` for animations
384
+ ---
301
385
 
302
- ## Browser Support
386
+ ## 🛠ïļ Development
303
387
 
304
- - Chrome 60+
305
- - Firefox 55+
306
- - Safari 11+
307
- - Edge 79+
388
+ ```bash
389
+ # Clone repository
390
+ git clone https://github.com/yourusername/reactjs-virtual-keyboard.git
308
391
 
309
- ## TypeScript
392
+ # Install dependencies
393
+ npm install
310
394
 
311
- All types are exported:
395
+ # Build library
396
+ npm run build
312
397
 
313
- ```tsx
314
- import type {
315
- VirtualKeyboardProps,
316
- VirtualKeyboardTheme,
317
- GlobalVirtualKeyboardProps,
318
- UseKeyboardScrollReturn,
319
- LayoutType,
320
- KeyboardLayoutProps,
321
- } from 'reactjs-virtual-keyboard';
398
+ # Run demo (if available)
399
+ cd demo && npm install && npm run dev
322
400
  ```
323
401
 
324
- ## License
402
+ ---
403
+
404
+ ## 📄 License
405
+
406
+ MIT ÂĐ Kalpesh Rane
407
+
408
+ ---
409
+
410
+ ## ðŸĪ Contributing
411
+
412
+ Contributions welcome! Please open an issue or submit a PR.
413
+
414
+ ---
415
+
416
+ ## 📝 Changelog
417
+
418
+ ### v2.0.0 (Latest)
419
+ - âœĻ **New**: Multi-language support with built-in language switcher
420
+ - âœĻ Added `languages`, `currentLanguage`, `onLanguageChange`, `showLanguageSwitcher` props
421
+ - âœĻ Enhanced customization API (24+ new props)
422
+ - ⚡ Removed unnecessary hook wrappers for better performance
423
+ - ðŸ“Ķ Optimized bundle size with better tree-shaking
424
+ - 🏗ïļ Reorganized file structure for clarity
425
+ - 🔧 Exported utility functions for advanced usage
426
+ - 📘 Improved TypeScript types with ReadonlyArray support
427
+ - 📚 Complete documentation website with interactive playground
325
428
 
326
- MIT ÂĐ kalpesh442266
429
+ ### v1.0.0
430
+ - 🎉 Initial release
327
431