UNPKG

4.39 kBJavaScriptView Raw
1'use strict';
2
3const KEYBOARD_DID_OPEN = 'ionKeyboardDidShow';
4const KEYBOARD_DID_CLOSE = 'ionKeyboardDidHide';
5const KEYBOARD_THRESHOLD = 150;
6let previousVisualViewport = {};
7let currentVisualViewport = {};
8let keyboardOpen = false;
9/**
10 * This is only used for tests
11 */
12const resetKeyboardAssist = () => {
13 previousVisualViewport = {};
14 currentVisualViewport = {};
15 keyboardOpen = false;
16};
17const startKeyboardAssist = (win) => {
18 startNativeListeners(win);
19 if (!win.visualViewport) {
20 return;
21 }
22 currentVisualViewport = copyVisualViewport(win.visualViewport);
23 win.visualViewport.onresize = () => {
24 trackViewportChanges(win);
25 if (keyboardDidOpen() || keyboardDidResize(win)) {
26 setKeyboardOpen(win);
27 }
28 else if (keyboardDidClose(win)) {
29 setKeyboardClose(win);
30 }
31 };
32};
33/**
34 * Listen for events fired by native keyboard plugin
35 * in Capacitor/Cordova so devs only need to listen
36 * in one place.
37 */
38const startNativeListeners = (win) => {
39 win.addEventListener('keyboardDidShow', ev => setKeyboardOpen(win, ev));
40 win.addEventListener('keyboardDidHide', () => setKeyboardClose(win));
41};
42const setKeyboardOpen = (win, ev) => {
43 fireKeyboardOpenEvent(win, ev);
44 keyboardOpen = true;
45};
46const setKeyboardClose = (win) => {
47 fireKeyboardCloseEvent(win);
48 keyboardOpen = false;
49};
50/**
51 * Returns `true` if the `keyboardOpen` flag is not
52 * set, the previous visual viewport width equal the current
53 * visual viewport width, and if the scaled difference
54 * of the previous visual viewport height minus the current
55 * visual viewport height is greater than KEYBOARD_THRESHOLD
56 *
57 * We need to be able to accommodate users who have zooming
58 * enabled in their browser (or have zoomed in manually) which
59 * is why we take into account the current visual viewport's
60 * scale value.
61 */
62const keyboardDidOpen = () => {
63 const scaledHeightDifference = (previousVisualViewport.height - currentVisualViewport.height) * currentVisualViewport.scale;
64 return (!keyboardOpen &&
65 previousVisualViewport.width === currentVisualViewport.width &&
66 scaledHeightDifference > KEYBOARD_THRESHOLD);
67};
68/**
69 * Returns `true` if the keyboard is open,
70 * but the keyboard did not close
71 */
72const keyboardDidResize = (win) => {
73 return keyboardOpen && !keyboardDidClose(win);
74};
75/**
76 * Determine if the keyboard was closed
77 * Returns `true` if the `keyboardOpen` flag is set and
78 * the current visual viewport height equals the
79 * layout viewport height.
80 */
81const keyboardDidClose = (win) => {
82 return keyboardOpen && currentVisualViewport.height === win.innerHeight;
83};
84/**
85 * Dispatch a keyboard open event
86 */
87const fireKeyboardOpenEvent = (win, nativeEv) => {
88 const keyboardHeight = nativeEv ? nativeEv.keyboardHeight : win.innerHeight - currentVisualViewport.height;
89 const ev = new CustomEvent(KEYBOARD_DID_OPEN, {
90 detail: { keyboardHeight }
91 });
92 win.dispatchEvent(ev);
93};
94/**
95 * Dispatch a keyboard close event
96 */
97const fireKeyboardCloseEvent = (win) => {
98 const ev = new CustomEvent(KEYBOARD_DID_CLOSE);
99 win.dispatchEvent(ev);
100};
101/**
102 * Given a window object, create a copy of
103 * the current visual and layout viewport states
104 * while also preserving the previous visual and
105 * layout viewport states
106 */
107const trackViewportChanges = (win) => {
108 previousVisualViewport = Object.assign({}, currentVisualViewport);
109 currentVisualViewport = copyVisualViewport(win.visualViewport);
110};
111/**
112 * Creates a deep copy of the visual viewport
113 * at a given state
114 */
115const copyVisualViewport = (visualViewport) => {
116 return {
117 width: Math.round(visualViewport.width),
118 height: Math.round(visualViewport.height),
119 offsetTop: visualViewport.offsetTop,
120 offsetLeft: visualViewport.offsetLeft,
121 pageTop: visualViewport.pageTop,
122 pageLeft: visualViewport.pageLeft,
123 scale: visualViewport.scale
124 };
125};
126
127exports.KEYBOARD_DID_CLOSE = KEYBOARD_DID_CLOSE;
128exports.KEYBOARD_DID_OPEN = KEYBOARD_DID_OPEN;
129exports.copyVisualViewport = copyVisualViewport;
130exports.keyboardDidClose = keyboardDidClose;
131exports.keyboardDidOpen = keyboardDidOpen;
132exports.keyboardDidResize = keyboardDidResize;
133exports.resetKeyboardAssist = resetKeyboardAssist;
134exports.setKeyboardClose = setKeyboardClose;
135exports.setKeyboardOpen = setKeyboardOpen;
136exports.startKeyboardAssist = startKeyboardAssist;
137exports.trackViewportChanges = trackViewportChanges;