@khanacademy/math-input 0.7.2 → 1.0.0
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/CHANGELOG.md +10 -0
- package/dist/actions/index.d.ts +31 -0
- package/dist/actions/index.js.flow +40 -0
- package/dist/components/compute-layout-parameters.d.ts +38 -0
- package/dist/components/compute-layout-parameters.js.flow +49 -0
- package/dist/components/corner-decal.d.ts +12 -0
- package/dist/components/corner-decal.js.flow +15 -0
- package/dist/components/echo-manager.d.ts +26 -0
- package/dist/components/echo-manager.js.flow +29 -0
- package/dist/components/empty-keypad-button.d.ts +13 -0
- package/dist/components/empty-keypad-button.js.flow +23 -0
- package/dist/components/expression-keypad.d.ts +22 -0
- package/dist/components/expression-keypad.js.flow +32 -0
- package/dist/components/fraction-keypad.d.ts +21 -0
- package/dist/components/fraction-keypad.js.flow +30 -0
- package/dist/components/gesture-manager.d.ts +74 -0
- package/dist/components/gesture-manager.js.flow +82 -0
- package/dist/components/gesture-state-machine.d.ts +105 -0
- package/dist/components/gesture-state-machine.js.flow +118 -0
- package/dist/components/icon.d.ts +15 -0
- package/dist/components/icon.js.flow +18 -0
- package/dist/components/input/__tests__/test-math-wrapper.d.ts +8 -0
- package/dist/components/input/__tests__/test-math-wrapper.js.flow +14 -0
- package/dist/components/input/cursor-handle.d.ts +1 -1
- package/dist/components/input/cursor-handle.js.flow +1 -1
- package/dist/components/input/drag-listener.d.ts +13 -0
- package/dist/components/input/drag-listener.js.flow +19 -0
- package/dist/components/input/math-input.d.ts +5 -4
- package/dist/components/input/math-input.js.flow +5 -4
- package/dist/components/input/math-wrapper.d.ts +110 -0
- package/dist/components/input/math-wrapper.js.flow +125 -0
- package/dist/components/input/scroll-into-view.d.ts +11 -0
- package/dist/components/input/scroll-into-view.js.flow +20 -0
- package/dist/components/keypad/button-assets.d.ts +4 -3
- package/dist/components/keypad/button-assets.js.flow +3 -3
- package/dist/components/keypad/button.d.ts +1 -2
- package/dist/components/keypad/button.js.flow +1 -2
- package/dist/components/keypad/keypad-page-items.d.ts +15 -10
- package/dist/components/keypad/keypad-page-items.js.flow +20 -10
- package/dist/components/keypad-button.d.ts +52 -0
- package/dist/components/keypad-button.js.flow +79 -0
- package/dist/components/keypad-container.d.ts +40 -0
- package/dist/components/keypad-container.js.flow +58 -0
- package/dist/components/keypad.d.ts +31 -0
- package/dist/components/keypad.js.flow +40 -0
- package/dist/components/many-keypad-button.d.ts +15 -0
- package/dist/components/many-keypad-button.js.flow +17 -0
- package/dist/components/math-icon.d.ts +16 -0
- package/dist/components/math-icon.js.flow +19 -0
- package/dist/components/multi-symbol-grid.d.ts +14 -0
- package/dist/components/multi-symbol-grid.js.flow +16 -0
- package/dist/components/multi-symbol-popover.d.ts +12 -0
- package/dist/components/multi-symbol-popover.js.flow +15 -0
- package/dist/components/navigation-pad.d.ts +14 -0
- package/dist/components/navigation-pad.js.flow +16 -0
- package/dist/components/node-manager.d.ts +53 -0
- package/dist/components/node-manager.js.flow +65 -0
- package/dist/components/popover-manager.d.ts +13 -0
- package/dist/components/popover-manager.js.flow +15 -0
- package/dist/components/popover-state-machine.d.ts +75 -0
- package/dist/components/popover-state-machine.js.flow +83 -0
- package/dist/components/provided-keypad.d.ts +8 -7
- package/dist/components/provided-keypad.js.flow +8 -7
- package/dist/components/styles.d.ts +6 -0
- package/dist/components/styles.js.flow +13 -0
- package/dist/components/svg-icon.d.ts +12 -0
- package/dist/components/svg-icon.js.flow +15 -0
- package/dist/components/tabbar/icons.d.ts +3 -2
- package/dist/components/tabbar/icons.js.flow +3 -2
- package/dist/components/tabbar/item.d.ts +1 -2
- package/dist/components/tabbar/item.js.flow +1 -2
- package/dist/components/tabbar/tabbar.d.ts +3 -3
- package/dist/components/tabbar/tabbar.js.flow +3 -3
- package/dist/components/text-icon.d.ts +13 -0
- package/dist/components/text-icon.js.flow +16 -0
- package/dist/components/touchable-keypad-button.d.ts +30 -0
- package/dist/components/touchable-keypad-button.js.flow +35 -0
- package/dist/components/two-page-keypad.d.ts +20 -0
- package/dist/components/two-page-keypad.js.flow +30 -0
- package/dist/components/velocity-tracker.d.ts +48 -0
- package/dist/components/velocity-tracker.js.flow +54 -0
- package/dist/es/index.js +938 -1059
- package/dist/es/index.js.map +1 -1
- package/dist/fake-react-native-web/text.d.ts +2 -1
- package/dist/fake-react-native-web/text.js.flow +2 -1
- package/dist/fake-react-native-web/view.d.ts +3 -2
- package/dist/fake-react-native-web/view.js.flow +3 -2
- package/dist/index.d.ts +1 -1
- package/dist/index.js +988 -1089
- package/dist/index.js.flow +1 -4
- package/dist/index.js.map +1 -1
- package/dist/store/echo-reducer.d.ts +5 -0
- package/dist/store/echo-reducer.js.flow +14 -0
- package/dist/store/index.d.ts +46 -1
- package/dist/store/index.js.flow +64 -1
- package/dist/store/input-reducer.d.ts +7 -0
- package/dist/store/input-reducer.js.flow +16 -0
- package/dist/store/keypad-reducer.d.ts +9 -0
- package/dist/store/keypad-reducer.js.flow +18 -0
- package/dist/store/layout-reducer.d.ts +21 -0
- package/dist/store/layout-reducer.js.flow +30 -0
- package/dist/store/pager-reducer.d.ts +13 -0
- package/dist/store/pager-reducer.js.flow +22 -0
- package/dist/store/shared.d.ts +6 -0
- package/dist/store/shared.js.flow +13 -0
- package/dist/store/types.d.ts +57 -0
- package/dist/store/types.js.flow +63 -0
- package/dist/types.d.ts +50 -0
- package/dist/types.js.flow +61 -0
- package/package.json +1 -1
- package/src/actions/{index.js → index.ts} +5 -5
- package/src/components/__tests__/{gesture-state-machine_test.js → gesture-state-machine.test.ts} +5 -1
- package/src/components/__tests__/{two-page-keypad_test.js → two-page-keypad.test.tsx} +0 -2
- package/src/components/{corner-decal.js → corner-decal.tsx} +6 -5
- package/src/components/{echo-manager.js → echo-manager.tsx} +29 -24
- package/src/components/{empty-keypad-button.js → empty-keypad-button.tsx} +17 -10
- package/src/components/{expression-keypad.js → expression-keypad.tsx} +27 -25
- package/src/components/{fraction-keypad.js → fraction-keypad.tsx} +21 -16
- package/src/components/{gesture-manager.js → gesture-manager.tsx} +10 -4
- package/src/components/{gesture-state-machine.js → gesture-state-machine.ts} +49 -3
- package/src/components/{icon.js → icon.tsx} +12 -14
- package/src/components/input/cursor-handle.tsx +1 -1
- package/src/components/input/{drag-listener.js → drag-listener.ts} +4 -0
- package/src/components/input/math-input.tsx +10 -9
- package/src/components/input/{math-wrapper.js → math-wrapper.ts} +10 -6
- package/src/components/input/{scroll-into-view.js → scroll-into-view.ts} +5 -15
- package/src/components/keypad/button-assets.tsx +4 -5
- package/src/components/keypad/button.tsx +1 -2
- package/src/components/keypad/index.tsx +1 -1
- package/src/components/keypad/keypad-page-items.tsx +33 -10
- package/src/components/{keypad-button.js → keypad-button.tsx} +42 -37
- package/src/components/{keypad-container.js → keypad-container.tsx} +41 -23
- package/src/components/{keypad.js → keypad.tsx} +31 -23
- package/src/components/{many-keypad-button.js → many-keypad-button.tsx} +8 -6
- package/src/components/{math-icon.js → math-icon.tsx} +7 -6
- package/src/components/{multi-symbol-grid.js → multi-symbol-grid.tsx} +8 -8
- package/src/components/{multi-symbol-popover.js → multi-symbol-popover.tsx} +5 -6
- package/src/components/{navigation-pad.js → navigation-pad.tsx} +7 -6
- package/src/components/{node-manager.js → node-manager.ts} +16 -4
- package/src/components/{popover-manager.js → popover-manager.tsx} +13 -16
- package/src/components/{popover-state-machine.js → popover-state-machine.ts} +21 -2
- package/src/components/prop-types.js +1 -67
- package/src/components/provided-keypad.tsx +14 -12
- package/src/components/{svg-icon.js → svg-icon.tsx} +5 -6
- package/src/components/tabbar/icons.tsx +4 -2
- package/src/components/tabbar/item.tsx +1 -3
- package/src/components/tabbar/{tabbar.stories.js → tabbar.stories.tsx} +10 -1
- package/src/components/tabbar/tabbar.tsx +3 -3
- package/src/components/{text-icon.js → text-icon.tsx} +7 -6
- package/src/components/{touchable-keypad-button.js → touchable-keypad-button.tsx} +19 -16
- package/src/components/{two-page-keypad.js → two-page-keypad.tsx} +13 -9
- package/src/components/{velocity-tracker.js → velocity-tracker.ts} +14 -4
- package/src/fake-react-native-web/text.tsx +2 -1
- package/src/fake-react-native-web/view.tsx +3 -2
- package/src/index.ts +1 -4
- package/src/store/echo-reducer.ts +58 -0
- package/src/store/index.ts +14 -425
- package/src/store/input-reducer.ts +55 -0
- package/src/store/keypad-reducer.ts +62 -0
- package/src/store/layout-reducer.ts +133 -0
- package/src/store/pager-reducer.ts +141 -0
- package/src/store/shared.ts +12 -0
- package/src/store/types.ts +65 -0
- package/src/types.ts +69 -0
- package/tsconfig.tsbuildinfo +1 -1
- package/src/components/app.js +0 -73
- package/src/demo.js +0 -9
- package/src/native-app.js +0 -85
- /package/src/components/__tests__/{node-manager_test.js → node-manager.test.ts} +0 -0
- /package/src/components/{compute-layout-parameters.js → compute-layout-parameters.ts} +0 -0
- /package/src/components/input/__tests__/{context-tracking_test.js → context-tracking.test.ts} +0 -0
- /package/src/components/input/__tests__/{mathquill_test.js → mathquill.test.ts} +0 -0
- /package/src/components/input/__tests__/{test-math-wrapper.jsx → test-math-wrapper.ts} +0 -0
- /package/src/components/keypad/{button.stories.js → button.stories.tsx} +0 -0
- /package/src/components/{styles.js → styles.ts} +0 -0
- /package/src/components/tabbar/__tests__/{tabbar_test.js → tabbar.test.tsx} +0 -0
|
@@ -11,18 +11,6 @@
|
|
|
11
11
|
|
|
12
12
|
import {toolbarHeightPx} from "../common-style";
|
|
13
13
|
|
|
14
|
-
// Taken from https://dev.opera.com/articles/fixing-the-scrolltop-bug/
|
|
15
|
-
function bodyOrHtml() {
|
|
16
|
-
if ("scrollingElement" in document) {
|
|
17
|
-
return document.scrollingElement;
|
|
18
|
-
}
|
|
19
|
-
// Fallback for legacy browsers
|
|
20
|
-
if (navigator.userAgent.indexOf("WebKit") !== -1) {
|
|
21
|
-
return document.body;
|
|
22
|
-
}
|
|
23
|
-
return document.documentElement;
|
|
24
|
-
}
|
|
25
|
-
|
|
26
14
|
export const scrollIntoView = (containerNode, keypadNode) => {
|
|
27
15
|
// TODO(charlie): There's no need for us to be reading the keypad bounds
|
|
28
16
|
// here, since they're pre-determined by logic in the store. We should
|
|
@@ -32,7 +20,7 @@ export const scrollIntoView = (containerNode, keypadNode) => {
|
|
|
32
20
|
const containerTopPx = containerBounds.top;
|
|
33
21
|
|
|
34
22
|
// Get the element that scrolls the document.
|
|
35
|
-
const scrollNode =
|
|
23
|
+
const scrollNode = document.scrollingElement;
|
|
36
24
|
|
|
37
25
|
const desiredMarginPx = 16;
|
|
38
26
|
|
|
@@ -58,7 +46,9 @@ export const scrollIntoView = (containerNode, keypadNode) => {
|
|
|
58
46
|
containerTopPx,
|
|
59
47
|
);
|
|
60
48
|
|
|
61
|
-
scrollNode
|
|
49
|
+
if (scrollNode) {
|
|
50
|
+
scrollNode.scrollTop += scrollOffset;
|
|
51
|
+
}
|
|
62
52
|
return;
|
|
63
53
|
}
|
|
64
54
|
}
|
|
@@ -66,7 +56,7 @@ export const scrollIntoView = (containerNode, keypadNode) => {
|
|
|
66
56
|
// Alternatively, if the input is out of the viewport or nearly out
|
|
67
57
|
// of the viewport, scroll it into view. We can do this regardless
|
|
68
58
|
// of whether the keypad has been provided.
|
|
69
|
-
if (containerTopPx < desiredMarginPx) {
|
|
59
|
+
if (scrollNode && containerTopPx < desiredMarginPx) {
|
|
70
60
|
scrollNode.scrollTop -= containerBounds.height + desiredMarginPx;
|
|
71
61
|
}
|
|
72
62
|
};
|
|
@@ -15,9 +15,9 @@ import * as React from "react";
|
|
|
15
15
|
// TODO: This should be an enumeration of all of the possible legal values
|
|
16
16
|
type KeyId = string;
|
|
17
17
|
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
18
|
+
type Props = {id: KeyId};
|
|
19
|
+
|
|
20
|
+
export default function ButtonAsset({id}: Props): React.ReactElement {
|
|
21
21
|
switch (id) {
|
|
22
22
|
case "NUM_0":
|
|
23
23
|
return (
|
|
@@ -489,5 +489,4 @@ const buttonAsset: React.FC<{
|
|
|
489
489
|
default:
|
|
490
490
|
throw new Error(`Invalid asset ${id}`);
|
|
491
491
|
}
|
|
492
|
-
}
|
|
493
|
-
export default buttonAsset;
|
|
492
|
+
}
|
|
@@ -65,8 +65,7 @@ type Props = {
|
|
|
65
65
|
tintColor?: string;
|
|
66
66
|
};
|
|
67
67
|
|
|
68
|
-
|
|
69
|
-
export default class Button extends React.Component<Props, State> {
|
|
68
|
+
export default class Button extends React.Component<Props> {
|
|
70
69
|
render(): React.ReactNode {
|
|
71
70
|
const {onPress, children, style, tintColor} = this.props;
|
|
72
71
|
return (
|
|
@@ -18,7 +18,7 @@ type State = {
|
|
|
18
18
|
selectedPage: TabbarItemType;
|
|
19
19
|
};
|
|
20
20
|
|
|
21
|
-
const allPages
|
|
21
|
+
const allPages = function (props: Props): React.ReactElement {
|
|
22
22
|
const pages: Array<TabbarItemType> = ["Numbers"];
|
|
23
23
|
|
|
24
24
|
if (props.preAlgebra) {
|
|
@@ -7,9 +7,13 @@ import ButtonAsset from "./button-assets";
|
|
|
7
7
|
import type {KeyConfig} from "../../data/key-configs";
|
|
8
8
|
import type {StyleType} from "@khanacademy/wonder-blocks-core";
|
|
9
9
|
|
|
10
|
-
|
|
10
|
+
type KeypadPageContainerProps = {
|
|
11
11
|
children: React.ReactNode;
|
|
12
|
-
}
|
|
12
|
+
};
|
|
13
|
+
|
|
14
|
+
export const KeypadPageContainer = ({
|
|
15
|
+
children,
|
|
16
|
+
}: KeypadPageContainerProps): React.ReactElement => (
|
|
13
17
|
<View
|
|
14
18
|
style={{
|
|
15
19
|
backgroundColor: "#DBDCDD",
|
|
@@ -25,12 +29,19 @@ export const KeypadPageContainer: React.FC<{
|
|
|
25
29
|
</View>
|
|
26
30
|
);
|
|
27
31
|
|
|
28
|
-
|
|
32
|
+
type KeypadButtonProps = {
|
|
29
33
|
keyConfig: KeyConfig;
|
|
30
34
|
tintColor?: string;
|
|
31
35
|
style?: StyleType;
|
|
32
36
|
onClickKey: (keyConfig: string) => void;
|
|
33
|
-
}
|
|
37
|
+
};
|
|
38
|
+
|
|
39
|
+
export const KeypadButton = ({
|
|
40
|
+
keyConfig,
|
|
41
|
+
onClickKey,
|
|
42
|
+
tintColor,
|
|
43
|
+
style,
|
|
44
|
+
}: KeypadButtonProps): React.ReactElement => (
|
|
34
45
|
<Button
|
|
35
46
|
onPress={() => onClickKey(keyConfig.id)}
|
|
36
47
|
tintColor={tintColor}
|
|
@@ -40,11 +51,17 @@ export const KeypadButton: React.FC<{
|
|
|
40
51
|
</Button>
|
|
41
52
|
);
|
|
42
53
|
|
|
43
|
-
|
|
54
|
+
type SecondaryKeypadButtonProps = {
|
|
44
55
|
keyConfig: KeyConfig;
|
|
45
|
-
style?:
|
|
56
|
+
style?: StyleType;
|
|
46
57
|
onClickKey: (keyConfig: string) => void;
|
|
47
|
-
}
|
|
58
|
+
};
|
|
59
|
+
|
|
60
|
+
export const SecondaryKeypadButton = ({
|
|
61
|
+
keyConfig,
|
|
62
|
+
onClickKey,
|
|
63
|
+
style,
|
|
64
|
+
}: SecondaryKeypadButtonProps): React.ReactElement => (
|
|
48
65
|
<KeypadButton
|
|
49
66
|
keyConfig={keyConfig}
|
|
50
67
|
onClickKey={onClickKey}
|
|
@@ -53,11 +70,17 @@ export const SecondaryKeypadButton: React.FC<{
|
|
|
53
70
|
/>
|
|
54
71
|
);
|
|
55
72
|
|
|
56
|
-
|
|
73
|
+
type KeypadActionButtonProps = {
|
|
57
74
|
keyConfig: KeyConfig;
|
|
58
|
-
style?:
|
|
75
|
+
style?: StyleType;
|
|
59
76
|
onClickKey: (keyConfig: string) => void;
|
|
60
|
-
}
|
|
77
|
+
};
|
|
78
|
+
|
|
79
|
+
export const KeypadActionButton = ({
|
|
80
|
+
keyConfig,
|
|
81
|
+
onClickKey,
|
|
82
|
+
style,
|
|
83
|
+
}: KeypadActionButtonProps): React.ReactElement => (
|
|
61
84
|
<KeypadButton
|
|
62
85
|
keyConfig={keyConfig}
|
|
63
86
|
onClickKey={onClickKey}
|
|
@@ -3,7 +3,6 @@
|
|
|
3
3
|
*/
|
|
4
4
|
|
|
5
5
|
import {StyleSheet, css} from "aphrodite";
|
|
6
|
-
import PropTypes from "prop-types";
|
|
7
6
|
import * as React from "react";
|
|
8
7
|
import {connect} from "react-redux";
|
|
9
8
|
|
|
@@ -23,36 +22,39 @@ import {
|
|
|
23
22
|
import CornerDecal from "./corner-decal";
|
|
24
23
|
import Icon from "./icon";
|
|
25
24
|
import MultiSymbolGrid from "./multi-symbol-grid";
|
|
26
|
-
|
|
25
|
+
|
|
26
|
+
import type {KeyType} from "../consts";
|
|
27
|
+
import type {State} from "../store/types";
|
|
28
|
+
import type {Border, KeyConfig, Icon as IconType} from "../types";
|
|
29
|
+
import type {StyleType} from "@khanacademy/wonder-blocks-core";
|
|
30
|
+
|
|
31
|
+
interface ReduxProps {
|
|
32
|
+
heightPx: number;
|
|
33
|
+
widthPx: number;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
interface Props extends ReduxProps {
|
|
37
|
+
ariaLabel?: string;
|
|
38
|
+
borders: Border;
|
|
39
|
+
childKeys: ReadonlyArray<KeyConfig>;
|
|
40
|
+
disabled: boolean;
|
|
41
|
+
focused: boolean;
|
|
42
|
+
popoverEnabled: boolean;
|
|
43
|
+
type: KeyType;
|
|
44
|
+
icon: IconType;
|
|
45
|
+
style?: StyleType;
|
|
46
|
+
onTouchCancel?: (evt: React.TouchEvent<HTMLDivElement>) => void;
|
|
47
|
+
onTouchEnd?: (evt: React.TouchEvent<HTMLDivElement>) => void;
|
|
48
|
+
onTouchMove?: (evt: React.TouchEvent<HTMLDivElement>) => void;
|
|
49
|
+
onTouchStart?: (evt: React.TouchEvent<HTMLDivElement>) => void;
|
|
50
|
+
// NOTE(matthewc)[LC-754] this is a normal React thing, but TS
|
|
51
|
+
// gets mad if I don't explicitly set it as a prop
|
|
52
|
+
ref?: (any) => void;
|
|
53
|
+
}
|
|
27
54
|
|
|
28
55
|
// eslint-disable-next-line react/no-unsafe
|
|
29
|
-
class KeypadButton extends React.PureComponent {
|
|
30
|
-
|
|
31
|
-
ariaLabel: PropTypes.string,
|
|
32
|
-
// The borders to display on the button. Typically, this should be set
|
|
33
|
-
// using one of the preset `BorderStyles` options.
|
|
34
|
-
borders: bordersPropType,
|
|
35
|
-
// Any additional keys that can be accessed by long-pressing on the
|
|
36
|
-
// button.
|
|
37
|
-
childKeys: PropTypes.arrayOf(keyConfigPropType),
|
|
38
|
-
// Whether the button should be rendered in a 'disabled' state, i.e.,
|
|
39
|
-
// without any touch feedback.
|
|
40
|
-
disabled: PropTypes.bool,
|
|
41
|
-
focused: PropTypes.bool,
|
|
42
|
-
heightPx: PropTypes.number.isRequired,
|
|
43
|
-
icon: iconPropType,
|
|
44
|
-
onTouchCancel: PropTypes.func,
|
|
45
|
-
onTouchEnd: PropTypes.func,
|
|
46
|
-
onTouchMove: PropTypes.func,
|
|
47
|
-
onTouchStart: PropTypes.func,
|
|
48
|
-
popoverEnabled: PropTypes.bool,
|
|
49
|
-
style: PropTypes.any,
|
|
50
|
-
type: PropTypes.oneOf(Object.keys(KeyTypes)).isRequired,
|
|
51
|
-
// NOTE(charlie): We may want to make this optional for phone layouts
|
|
52
|
-
// (and rely on Flexbox instead), since it might not be pixel perfect
|
|
53
|
-
// with borders and such.
|
|
54
|
-
widthPx: PropTypes.number.isRequired,
|
|
55
|
-
};
|
|
56
|
+
class KeypadButton extends React.PureComponent<Props> {
|
|
57
|
+
buttonSizeStyle: StyleType | undefined;
|
|
56
58
|
|
|
57
59
|
static defaultProps = {
|
|
58
60
|
borders: BorderStyles.ALL,
|
|
@@ -126,7 +128,7 @@ class KeypadButton extends React.PureComponent {
|
|
|
126
128
|
return [styles.focusBox, focusBackgroundStyle];
|
|
127
129
|
};
|
|
128
130
|
|
|
129
|
-
_getButtonStyle = (type, borders, style) => {
|
|
131
|
+
_getButtonStyle = (type, borders, style?) => {
|
|
130
132
|
// Select the appropriate style for the button.
|
|
131
133
|
let backgroundStyle;
|
|
132
134
|
switch (type) {
|
|
@@ -154,10 +156,12 @@ class KeypadButton extends React.PureComponent {
|
|
|
154
156
|
}
|
|
155
157
|
|
|
156
158
|
const borderStyle = [];
|
|
157
|
-
if (borders.
|
|
159
|
+
if (borders.includes(BorderDirections.LEFT)) {
|
|
160
|
+
// @ts-expect-error TS2345
|
|
158
161
|
borderStyle.push(styles.leftBorder);
|
|
159
162
|
}
|
|
160
|
-
if (borders.
|
|
163
|
+
if (borders.includes(BorderDirections.BOTTOM)) {
|
|
164
|
+
// @ts-expect-error TS2345
|
|
161
165
|
borderStyle.push(styles.bottomBorder);
|
|
162
166
|
}
|
|
163
167
|
|
|
@@ -199,7 +203,7 @@ class KeypadButton extends React.PureComponent {
|
|
|
199
203
|
const focusStyle = this._getFocusStyle(type);
|
|
200
204
|
const iconWrapperStyle = [
|
|
201
205
|
styles.iconWrapper,
|
|
202
|
-
disabled
|
|
206
|
+
disabled ? styles.disabled : undefined,
|
|
203
207
|
];
|
|
204
208
|
|
|
205
209
|
const eventHandlers = {
|
|
@@ -267,8 +271,6 @@ const focusBoxZIndex = 0;
|
|
|
267
271
|
|
|
268
272
|
const styles = StyleSheet.create({
|
|
269
273
|
buttonBase: {
|
|
270
|
-
// HACK(benkomalo): support old style flex box in Android browsers
|
|
271
|
-
"-webkit-box-flex": "1",
|
|
272
274
|
flex: 1,
|
|
273
275
|
cursor: "pointer",
|
|
274
276
|
// Make the text unselectable
|
|
@@ -353,8 +355,11 @@ const styleForButtonDimensions = (heightPx, widthPx) => {
|
|
|
353
355
|
}).buttonSize;
|
|
354
356
|
};
|
|
355
357
|
|
|
356
|
-
const mapStateToProps = (state) => {
|
|
357
|
-
return
|
|
358
|
+
const mapStateToProps = (state: State): ReduxProps => {
|
|
359
|
+
return {
|
|
360
|
+
heightPx: state.layout.buttonDimensions.heightPx,
|
|
361
|
+
widthPx: state.layout.buttonDimensions.widthPx,
|
|
362
|
+
};
|
|
358
363
|
};
|
|
359
364
|
|
|
360
365
|
export default connect(mapStateToProps, null, null, {forwardRef: true})(
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
import {StyleSheet} from "aphrodite";
|
|
2
|
-
import PropTypes from "prop-types";
|
|
3
2
|
import * as React from "react";
|
|
4
3
|
import {connect} from "react-redux";
|
|
5
4
|
|
|
@@ -16,27 +15,39 @@ import {
|
|
|
16
15
|
import ExpressionKeypad from "./expression-keypad";
|
|
17
16
|
import FractionKeypad from "./fraction-keypad";
|
|
18
17
|
import NavigationPad from "./navigation-pad";
|
|
19
|
-
import {keyIdPropType} from "./prop-types";
|
|
20
18
|
import Styles from "./styles";
|
|
21
19
|
import * as zIndexes from "./z-indexes";
|
|
22
20
|
|
|
21
|
+
import type {KeypadType} from "../consts";
|
|
22
|
+
import type {State as ReduxState} from "../store/types";
|
|
23
|
+
import type {StyleType} from "@khanacademy/wonder-blocks-core";
|
|
24
|
+
|
|
23
25
|
const {row, centered, fullWidth} = Styles;
|
|
24
26
|
|
|
27
|
+
interface ReduxProps {
|
|
28
|
+
active?: boolean;
|
|
29
|
+
extraKeys?: ReadonlyArray<string>;
|
|
30
|
+
keypadType?: KeypadType;
|
|
31
|
+
layoutMode?: keyof typeof LayoutModes;
|
|
32
|
+
navigationPadEnabled?: boolean;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
interface Props extends ReduxProps {
|
|
36
|
+
onDismiss?: () => void;
|
|
37
|
+
onElementMounted: (element: any) => void;
|
|
38
|
+
onPageSizeChange?: (width: number, height: number) => void;
|
|
39
|
+
style?: StyleType;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
type State = {
|
|
43
|
+
hasBeenActivated: boolean;
|
|
44
|
+
viewportWidth: string | number;
|
|
45
|
+
};
|
|
46
|
+
|
|
25
47
|
// eslint-disable-next-line react/no-unsafe
|
|
26
|
-
class KeypadContainer extends React.Component {
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
extraKeys: PropTypes.arrayOf(keyIdPropType),
|
|
30
|
-
keypadType: PropTypes.oneOf(Object.keys(KeypadTypes)).isRequired,
|
|
31
|
-
layoutMode: PropTypes.oneOf(Object.keys(LayoutModes)).isRequired,
|
|
32
|
-
navigationPadEnabled: PropTypes.bool.isRequired,
|
|
33
|
-
onDismiss: PropTypes.func,
|
|
34
|
-
// A callback that should be triggered with the root React element on
|
|
35
|
-
// mount.
|
|
36
|
-
onElementMounted: PropTypes.func,
|
|
37
|
-
onPageSizeChange: PropTypes.func.isRequired,
|
|
38
|
-
style: PropTypes.any,
|
|
39
|
-
};
|
|
48
|
+
class KeypadContainer extends React.Component<Props, State> {
|
|
49
|
+
_resizeTimeout: number | null | undefined;
|
|
50
|
+
hasMounted: boolean | undefined;
|
|
40
51
|
|
|
41
52
|
state = {
|
|
42
53
|
hasBeenActivated: false,
|
|
@@ -89,7 +100,7 @@ class KeypadContainer extends React.Component {
|
|
|
89
100
|
// Throttle the resize callbacks.
|
|
90
101
|
// https://developer.mozilla.org/en-US/docs/Web/Events/resize
|
|
91
102
|
if (this._resizeTimeout == null) {
|
|
92
|
-
this._resizeTimeout = setTimeout(() => {
|
|
103
|
+
this._resizeTimeout = window.setTimeout(() => {
|
|
93
104
|
this._resizeTimeout = null;
|
|
94
105
|
|
|
95
106
|
this._onResize();
|
|
@@ -103,8 +114,7 @@ class KeypadContainer extends React.Component {
|
|
|
103
114
|
this.setState({
|
|
104
115
|
viewportWidth: window.innerWidth,
|
|
105
116
|
});
|
|
106
|
-
|
|
107
|
-
this.props.onPageSizeChange(window.innerWidth, window.innerHeight);
|
|
117
|
+
this.props.onPageSizeChange?.(window.innerWidth, window.innerHeight);
|
|
108
118
|
};
|
|
109
119
|
|
|
110
120
|
renderKeypad = () => {
|
|
@@ -154,11 +164,17 @@ class KeypadContainer extends React.Component {
|
|
|
154
164
|
// NOTE(charlie): We render the transforms as pure inline styles to
|
|
155
165
|
// avoid an Aphrodite bug in mobile Safari.
|
|
156
166
|
// See: https://github.com/Khan/aphrodite/issues/68.
|
|
157
|
-
|
|
167
|
+
let dynamicStyle = {
|
|
158
168
|
...(active ? inlineStyles.active : inlineStyles.hidden),
|
|
159
|
-
...(!active && !hasBeenActivated ? inlineStyles.invisible : {}),
|
|
160
169
|
};
|
|
161
170
|
|
|
171
|
+
if (!active && !hasBeenActivated) {
|
|
172
|
+
dynamicStyle = {
|
|
173
|
+
...dynamicStyle,
|
|
174
|
+
...inlineStyles.invisible,
|
|
175
|
+
};
|
|
176
|
+
}
|
|
177
|
+
|
|
162
178
|
const keypadContainerStyle = [
|
|
163
179
|
row,
|
|
164
180
|
centered,
|
|
@@ -278,9 +294,11 @@ const inlineStyles = {
|
|
|
278
294
|
},
|
|
279
295
|
};
|
|
280
296
|
|
|
281
|
-
const mapStateToProps = (state) => {
|
|
297
|
+
const mapStateToProps = (state: ReduxState): ReduxProps => {
|
|
282
298
|
return {
|
|
283
|
-
|
|
299
|
+
extraKeys: state.keypad.extraKeys,
|
|
300
|
+
keypadType: state.keypad.keypadType,
|
|
301
|
+
active: state.keypad.active,
|
|
284
302
|
layoutMode: state.layout.layoutMode,
|
|
285
303
|
navigationPadEnabled: state.layout.navigationPadEnabled,
|
|
286
304
|
};
|
|
@@ -3,7 +3,6 @@
|
|
|
3
3
|
* and manages the rendering of echo animations on top of those buttons.
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
import PropTypes from "prop-types";
|
|
7
6
|
import * as React from "react";
|
|
8
7
|
import ReactDOM from "react-dom";
|
|
9
8
|
import {connect} from "react-redux";
|
|
@@ -13,26 +12,28 @@ import {View} from "../fake-react-native-web/index";
|
|
|
13
12
|
|
|
14
13
|
import EchoManager from "./echo-manager";
|
|
15
14
|
import PopoverManager from "./popover-manager";
|
|
16
|
-
|
|
15
|
+
|
|
16
|
+
import type {State} from "../store/types";
|
|
17
|
+
import type {Popover, Echo} from "../types";
|
|
18
|
+
import type {StyleType} from "@khanacademy/wonder-blocks-core";
|
|
19
|
+
|
|
20
|
+
interface ReduxProps {
|
|
21
|
+
active: boolean;
|
|
22
|
+
echoes: ReadonlyArray<Echo>;
|
|
23
|
+
popover: Popover | null;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
interface Props extends ReduxProps {
|
|
27
|
+
children: React.ReactNode;
|
|
28
|
+
style?: StyleType;
|
|
29
|
+
removeEcho?: (animationId: string) => void;
|
|
30
|
+
}
|
|
17
31
|
|
|
18
32
|
// eslint-disable-next-line react/no-unsafe
|
|
19
|
-
class Keypad extends React.Component {
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
PropTypes.node,
|
|
24
|
-
]),
|
|
25
|
-
removeEcho: PropTypes.func.isRequired,
|
|
26
|
-
style: PropTypes.any,
|
|
27
|
-
|
|
28
|
-
// The props below are injected by redux
|
|
29
|
-
|
|
30
|
-
// Whether the keypad is active, i.e., whether it should be rendered as
|
|
31
|
-
// visible or invisible.
|
|
32
|
-
active: PropTypes.bool,
|
|
33
|
-
echoes: PropTypes.arrayOf(echoPropType).isRequired,
|
|
34
|
-
popover: popoverPropType,
|
|
35
|
-
};
|
|
33
|
+
class Keypad extends React.Component<Props> {
|
|
34
|
+
_isMounted: boolean | undefined;
|
|
35
|
+
_resizeTimeout: number | null | undefined;
|
|
36
|
+
_container: DOMRect | null | undefined;
|
|
36
37
|
|
|
37
38
|
componentDidMount() {
|
|
38
39
|
this._isMounted = true;
|
|
@@ -54,7 +55,7 @@ class Keypad extends React.Component {
|
|
|
54
55
|
}
|
|
55
56
|
|
|
56
57
|
_computeContainer = () => {
|
|
57
|
-
const domNode = ReactDOM.findDOMNode(this);
|
|
58
|
+
const domNode = ReactDOM.findDOMNode(this) as Element;
|
|
58
59
|
this._container = domNode.getBoundingClientRect();
|
|
59
60
|
};
|
|
60
61
|
|
|
@@ -76,7 +77,7 @@ class Keypad extends React.Component {
|
|
|
76
77
|
// Throttle resize events -- taken from:
|
|
77
78
|
// https://developer.mozilla.org/en-US/docs/Web/Events/resize
|
|
78
79
|
if (this._resizeTimeout == null) {
|
|
79
|
-
this._resizeTimeout = setTimeout(() => {
|
|
80
|
+
this._resizeTimeout = window.setTimeout(() => {
|
|
80
81
|
this._resizeTimeout = null;
|
|
81
82
|
|
|
82
83
|
if (this._isMounted) {
|
|
@@ -96,9 +97,13 @@ class Keypad extends React.Component {
|
|
|
96
97
|
return {
|
|
97
98
|
...rest,
|
|
98
99
|
initialBounds: {
|
|
100
|
+
// @ts-expect-error TS2533
|
|
99
101
|
top: initialBounds.top - this._container.top,
|
|
102
|
+
// @ts-expect-error TS2533
|
|
100
103
|
right: initialBounds.right - this._container.left,
|
|
104
|
+
// @ts-expect-error TS2533
|
|
101
105
|
bottom: initialBounds.bottom - this._container.top,
|
|
106
|
+
// @ts-expect-error TS2533
|
|
102
107
|
left: initialBounds.left - this._container.left,
|
|
103
108
|
width: initialBounds.width,
|
|
104
109
|
height: initialBounds.height,
|
|
@@ -113,8 +118,11 @@ class Keypad extends React.Component {
|
|
|
113
118
|
...popover,
|
|
114
119
|
bounds: {
|
|
115
120
|
bottom:
|
|
121
|
+
// @ts-expect-error TS2533
|
|
116
122
|
this._container.height -
|
|
123
|
+
// @ts-expect-error TS2533
|
|
117
124
|
(popover.bounds.bottom - this._container.top),
|
|
125
|
+
// @ts-expect-error TS2533
|
|
118
126
|
left: popover.bounds.left - this._container.left,
|
|
119
127
|
width: popover.bounds.width,
|
|
120
128
|
},
|
|
@@ -133,9 +141,9 @@ class Keypad extends React.Component {
|
|
|
133
141
|
}
|
|
134
142
|
}
|
|
135
143
|
|
|
136
|
-
const mapStateToProps = (state) => {
|
|
144
|
+
const mapStateToProps = (state: State): ReduxProps => {
|
|
137
145
|
return {
|
|
138
|
-
|
|
146
|
+
echoes: state.echoes.echoes,
|
|
139
147
|
active: state.keypad.active,
|
|
140
148
|
popover: state.gestures.popover,
|
|
141
149
|
};
|
|
@@ -3,7 +3,6 @@
|
|
|
3
3
|
* 'default' symbol.
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
import PropTypes from "prop-types";
|
|
7
6
|
import * as React from "react";
|
|
8
7
|
|
|
9
8
|
import {KeyTypes} from "../consts";
|
|
@@ -11,12 +10,15 @@ import KeyConfigs from "../data/key-configs";
|
|
|
11
10
|
import Keys from "../data/keys";
|
|
12
11
|
|
|
13
12
|
import EmptyKeypadButton from "./empty-keypad-button";
|
|
14
|
-
import {keyIdPropType} from "./prop-types";
|
|
15
13
|
import TouchableKeypadButton from "./touchable-keypad-button";
|
|
16
14
|
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
15
|
+
type Props = {
|
|
16
|
+
keys: ReadonlyArray<string>;
|
|
17
|
+
};
|
|
18
|
+
|
|
19
|
+
class ManyKeypadButton extends React.Component<Props> {
|
|
20
|
+
static defaultProps = {
|
|
21
|
+
keys: [],
|
|
20
22
|
};
|
|
21
23
|
|
|
22
24
|
render() {
|
|
@@ -26,7 +28,7 @@ class ManyKeypadButton extends React.Component {
|
|
|
26
28
|
// one, render a standard button. Otherwise, capture them all in a
|
|
27
29
|
// single button.
|
|
28
30
|
if (keys.length === 0) {
|
|
29
|
-
return <EmptyKeypadButton
|
|
31
|
+
return <EmptyKeypadButton />;
|
|
30
32
|
} else if (keys.length === 1) {
|
|
31
33
|
const keyConfig = KeyConfigs[keys[0]];
|
|
32
34
|
return <TouchableKeypadButton keyConfig={keyConfig} {...rest} />;
|
|
@@ -4,7 +4,6 @@
|
|
|
4
4
|
|
|
5
5
|
import {StyleSheet} from "aphrodite";
|
|
6
6
|
import katex from "katex";
|
|
7
|
-
import PropTypes from "prop-types";
|
|
8
7
|
import * as React from "react";
|
|
9
8
|
import ReactDOM from "react-dom";
|
|
10
9
|
|
|
@@ -13,14 +12,16 @@ import {View} from "../fake-react-native-web/index";
|
|
|
13
12
|
import {iconSizeHeightPx, iconSizeWidthPx} from "./common-style";
|
|
14
13
|
import Styles from "./styles";
|
|
15
14
|
|
|
15
|
+
import type {StyleType} from "@khanacademy/wonder-blocks-core";
|
|
16
|
+
|
|
16
17
|
const {row, centered} = Styles;
|
|
17
18
|
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
};
|
|
19
|
+
type Props = {
|
|
20
|
+
math: string;
|
|
21
|
+
style: StyleType;
|
|
22
|
+
};
|
|
23
23
|
|
|
24
|
+
class MathIcon extends React.Component<Props> {
|
|
24
25
|
componentDidMount() {
|
|
25
26
|
this._renderMath();
|
|
26
27
|
}
|
|
@@ -4,7 +4,6 @@
|
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
6
|
import {StyleSheet} from "aphrodite";
|
|
7
|
-
import PropTypes from "prop-types";
|
|
8
7
|
import * as React from "react";
|
|
9
8
|
|
|
10
9
|
import {IconTypes} from "../consts";
|
|
@@ -12,17 +11,18 @@ import {View} from "../fake-react-native-web/index";
|
|
|
12
11
|
|
|
13
12
|
import {iconSizeHeightPx, iconSizeWidthPx} from "./common-style";
|
|
14
13
|
import Icon from "./icon";
|
|
15
|
-
import {iconPropType} from "./prop-types";
|
|
16
14
|
import Styles from "./styles";
|
|
17
15
|
|
|
16
|
+
import type {Icon as IconType} from "../types";
|
|
17
|
+
|
|
18
18
|
const {row, column, centered, fullWidth} = Styles;
|
|
19
19
|
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
};
|
|
20
|
+
type Props = {
|
|
21
|
+
focused: boolean;
|
|
22
|
+
icons: ReadonlyArray<IconType>;
|
|
23
|
+
};
|
|
25
24
|
|
|
25
|
+
class MultiSymbolGrid extends React.Component<Props> {
|
|
26
26
|
render() {
|
|
27
27
|
const {focused, icons} = this.props;
|
|
28
28
|
|
|
@@ -131,7 +131,7 @@ class MultiSymbolGrid extends React.Component {
|
|
|
131
131
|
}
|
|
132
132
|
}
|
|
133
133
|
|
|
134
|
-
throw new Error(
|
|
134
|
+
throw new Error(`Invalid number of icons: ${icons.length}`);
|
|
135
135
|
}
|
|
136
136
|
}
|
|
137
137
|
|
|
@@ -3,21 +3,20 @@
|
|
|
3
3
|
*/
|
|
4
4
|
|
|
5
5
|
import {StyleSheet} from "aphrodite";
|
|
6
|
-
import PropTypes from "prop-types";
|
|
7
6
|
import * as React from "react";
|
|
8
7
|
|
|
9
8
|
import {BorderStyles} from "../consts";
|
|
10
9
|
import {View} from "../fake-react-native-web/index";
|
|
10
|
+
import {KeyConfig} from "../types";
|
|
11
11
|
|
|
12
|
-
import {keyConfigPropType} from "./prop-types";
|
|
13
12
|
import TouchableKeypadButton from "./touchable-keypad-button";
|
|
14
13
|
import * as zIndexes from "./z-indexes";
|
|
15
14
|
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
};
|
|
15
|
+
type Prop = {
|
|
16
|
+
keys: ReadonlyArray<KeyConfig>;
|
|
17
|
+
};
|
|
20
18
|
|
|
19
|
+
class MultiSymbolPopover extends React.Component<Prop> {
|
|
21
20
|
render() {
|
|
22
21
|
const {keys} = this.props;
|
|
23
22
|
|