@ovotech/element-native 5.3.0 → 5.4.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/dist/d.d.ts +4 -0
- package/dist/esm/src/components/Button/Button.js +2 -1
- package/dist/esm/src/components/Button/Button.styles.js +4 -1
- package/dist/esm/src/components/CurrencyField/CurrencyField.js +2 -2
- package/dist/esm/src/components/EmailField/EmailField.js +2 -2
- package/dist/esm/src/components/Grid/Col.js +14 -12
- package/dist/esm/src/components/Grid/Row.js +6 -10
- package/dist/esm/src/components/Heading/Heading.js +1 -1
- package/dist/esm/src/components/NavHeader/NavHeader.js +126 -29
- package/dist/esm/src/components/NavHeader/NavHeader.styles.js +84 -54
- package/dist/esm/src/components/NavHeader/NavHeaderComponents/ActionButtons.js +12 -0
- package/dist/esm/src/components/NavHeader/NavHeaderComponents/NavButton.js +23 -0
- package/dist/esm/src/components/NavHeader/NavHeaderComponents/StepCounterBars.js +5 -0
- package/dist/esm/src/components/NavHeader/utils.js +23 -0
- package/dist/esm/src/components/PasswordField/PasswordField.js +2 -2
- package/dist/esm/src/components/PasswordInput/PasswordInput.js +1 -1
- package/dist/esm/src/components/PhoneField/PhoneField.js +2 -2
- package/dist/esm/src/components/ScreenView/ScreenView.js +33 -0
- package/dist/esm/src/components/ScreenView/index.js +1 -0
- package/dist/esm/src/components/SegmentedControls/components/SegmentButton.js +1 -1
- package/dist/esm/src/components/SelectField/Select.js +5 -4
- package/dist/esm/src/components/SelectField/SelectField.js +1 -1
- package/dist/esm/src/components/TextField/TextField.js +2 -2
- package/dist/esm/src/components/TextInput/TextInput.js +1 -1
- package/dist/esm/src/components/TextareaField/TextareaField.js +2 -2
- package/dist/esm/src/components/Toggle/styles.js +1 -1
- package/dist/esm/src/components/index.js +1 -0
- package/dist/esm/src/hooks/index.js +1 -1
- package/dist/esm/src/hooks/use-full-width.js +1 -1
- package/dist/src/components/Button/Button.d.ts +3 -2
- package/dist/src/components/Button/Button.js +2 -1
- package/dist/src/components/Button/Button.styles.d.ts +1 -1
- package/dist/src/components/Button/Button.styles.js +4 -1
- package/dist/src/components/Cards/IconDataCard/IconDataCard.styles.d.ts +2 -2
- package/dist/src/components/Cards/LinkTextCard/LinkTextCard.styles.d.ts +1 -1
- package/dist/src/components/CurrencyField/CurrencyField.d.ts +1 -1
- package/dist/src/components/CurrencyField/CurrencyField.js +2 -2
- package/dist/src/components/EmailField/EmailField.d.ts +1 -1
- package/dist/src/components/EmailField/EmailField.js +2 -2
- package/dist/src/components/Grid/Col.js +14 -12
- package/dist/src/components/Grid/Row.js +6 -10
- package/dist/src/components/Heading/Heading.d.ts +3 -1
- package/dist/src/components/Heading/Heading.js +1 -1
- package/dist/src/components/NavHeader/NavHeader.d.ts +24 -21
- package/dist/src/components/NavHeader/NavHeader.js +126 -29
- package/dist/src/components/NavHeader/NavHeader.styles.d.ts +2320 -20
- package/dist/src/components/NavHeader/NavHeader.styles.js +84 -54
- package/dist/src/components/NavHeader/NavHeaderComponents/ActionButtons.d.ts +3 -0
- package/dist/src/components/NavHeader/NavHeaderComponents/ActionButtons.js +12 -0
- package/dist/src/components/NavHeader/NavHeaderComponents/NavButton.d.ts +11 -0
- package/dist/src/components/NavHeader/NavHeaderComponents/NavButton.js +23 -0
- package/dist/src/components/NavHeader/NavHeaderComponents/StepCounterBars.d.ts +7 -0
- package/dist/src/components/NavHeader/NavHeaderComponents/StepCounterBars.js +5 -0
- package/dist/src/components/NavHeader/utils.d.ts +9 -0
- package/dist/src/components/NavHeader/utils.js +23 -0
- package/dist/src/components/PasswordField/PasswordField.d.ts +1 -1
- package/dist/src/components/PasswordField/PasswordField.js +2 -2
- package/dist/src/components/PasswordInput/PasswordInput.js +1 -1
- package/dist/src/components/PhoneField/PhoneField.d.ts +1 -1
- package/dist/src/components/PhoneField/PhoneField.js +2 -2
- package/dist/src/components/ScreenView/ScreenView.d.ts +5 -0
- package/dist/src/components/ScreenView/ScreenView.js +33 -0
- package/dist/src/components/ScreenView/index.d.ts +1 -0
- package/dist/src/components/ScreenView/index.js +1 -0
- package/dist/src/components/SegmentedControls/components/SegmentButton.js +1 -1
- package/dist/src/components/SelectField/Select.d.ts +3 -1
- package/dist/src/components/SelectField/Select.js +5 -4
- package/dist/src/components/SelectField/SelectField.d.ts +4 -1
- package/dist/src/components/SelectField/SelectField.js +1 -1
- package/dist/src/components/TextField/TextField.d.ts +1 -1
- package/dist/src/components/TextField/TextField.js +2 -2
- package/dist/src/components/TextInput/TextInput.d.ts +5 -3
- package/dist/src/components/TextInput/TextInput.js +1 -1
- package/dist/src/components/TextareaField/TextareaField.d.ts +1 -1
- package/dist/src/components/TextareaField/TextareaField.js +2 -2
- package/dist/src/components/Toggle/styles.js +1 -1
- package/dist/src/components/index.d.ts +1 -0
- package/dist/src/components/index.js +1 -0
- package/dist/src/hooks/index.d.ts +1 -1
- package/dist/src/hooks/index.js +1 -1
- package/dist/src/hooks/use-full-width.js +1 -1
- package/package.json +2 -1
- /package/dist/esm/src/hooks/{use-breakpoint.js → use-breakpoint.native.js} +0 -0
- /package/dist/src/hooks/{use-breakpoint.d.ts → use-breakpoint.native.d.ts} +0 -0
- /package/dist/src/hooks/{use-breakpoint.js → use-breakpoint.native.js} +0 -0
|
@@ -2,7 +2,8 @@ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
|
2
2
|
import { numToPx } from '@ovotech/element-core';
|
|
3
3
|
import groupBy from 'lodash.groupby';
|
|
4
4
|
import { Fragment, useState } from 'react';
|
|
5
|
-
import { Dimensions, Modal, ScrollView, View } from 'react-native';
|
|
5
|
+
import { Dimensions, Modal, ScrollView, View, } from 'react-native';
|
|
6
|
+
import { SafeAreaView } from 'react-native-safe-area-context';
|
|
6
7
|
import styled, { css } from '../../styled.native';
|
|
7
8
|
import { Icon } from '../Icon';
|
|
8
9
|
import { P } from '../P';
|
|
@@ -30,7 +31,7 @@ const DropdownWrapper = styled.TouchableOpacity(({ theme }) => css `
|
|
|
30
31
|
/* 80 is an opacity for hex https://gist.github.com/lopspower/03fb1cc0ac9f32ef38f4 */
|
|
31
32
|
background-color: ${theme.color.brand.dark}80;
|
|
32
33
|
`);
|
|
33
|
-
const DropdownContainer = styled
|
|
34
|
+
const DropdownContainer = styled(SafeAreaView)(({ theme }) => css `
|
|
34
35
|
width: 95%;
|
|
35
36
|
max-height: 70%;
|
|
36
37
|
border-radius: ${numToPx(theme.border.radius.sm)};
|
|
@@ -74,7 +75,7 @@ const StyledCategory = styled(P)(({ theme }) => css `
|
|
|
74
75
|
background-color: ${theme.color.surface.surface};
|
|
75
76
|
padding: ${numToPx(theme.space[100])} ${numToPx(theme.space[400])};
|
|
76
77
|
`);
|
|
77
|
-
export const Select = ({ options = [], defaultSelected = { label: '', value: 'default' }, noOptionMessage = 'No option selected', onSelected = () => null, hasError = false, testID = 'select', }) => {
|
|
78
|
+
export const Select = ({ options = [], defaultSelected = { label: '', value: 'default' }, noOptionMessage = 'No option selected', onSelected = () => null, hasError = false, testID = 'select', ref, }) => {
|
|
78
79
|
const [isOpen, setOpen] = useState(false);
|
|
79
80
|
const [selected, setSelected] = useState(defaultSelected);
|
|
80
81
|
const height = Dimensions.get('window').height;
|
|
@@ -89,5 +90,5 @@ export const Select = ({ options = [], defaultSelected = { label: '', value: 'de
|
|
|
89
90
|
label: `-- ${noOptionMessage} --`,
|
|
90
91
|
value: 'default',
|
|
91
92
|
};
|
|
92
|
-
return (_jsxs(View, { children: [_jsxs(SelectInput, { testID: testID, hasError: hasError, onPress: () => setOpen(!isOpen), children: [_jsx(P, { style: { marginTop: 0, marginBottom: 0 }, children: selected.value === 'default' ? '' : selected.label }), _jsx(Icon, { name: "chevron-down", size: 16, style: { marginLeft: 'auto' } })] }), _jsx(Modal, { transparent: true, visible: isOpen, animationType: "fade", onRequestClose: () => setOpen(false), children: _jsx(DropdownWrapper, { onPress: () => setOpen(false), children: _jsx(DropdownContainer, { style: { maxHeight: dropdownContainerMaxHeight }, children: _jsxs(ScrollView, { nestedScrollEnabled: true, testID: `${testID}-OptionsScrollView`, children: [_jsxs(SelectOption, { accessible: true, accessibilityRole: "radio", onPress: () => handleOptionPress(requiredOption), children: [_jsx(StyledP, { children: _jsx(Strong, { children: requiredOption.label }) }), _jsx(Radio, { isChecked: selected.value === requiredOption.value, children: _jsx(RadioDot, { isChecked: selected.value === requiredOption.value }) })] }), Object.keys(optionsByCategories).map(category => (_jsxs(Fragment, { children: [category !== 'undefined' ? (_jsx(StyledCategory, { children: category })) : null, optionsByCategories[category].map((option, i) => (_jsxs(SelectOption, { accessible: true, accessibilityRole: "radio", isLastOption: i === optionsByCategories[category].length - 1, onPress: () => handleOptionPress(option), children: [_jsx(StyledP, { children: _jsx(Strong, { children: option.label }) }), _jsx(Radio, { isChecked: selected.value === option.value, children: _jsx(RadioDot, { isChecked: selected.value === option.value }) })] }, option.label)))] }, category)))] }) }) }) })] }));
|
|
93
|
+
return (_jsxs(View, { children: [_jsxs(SelectInput, { testID: testID, hasError: hasError, onPress: () => setOpen(!isOpen), ref: ref, children: [_jsx(P, { style: { marginTop: 0, marginBottom: 0 }, children: selected.value === 'default' ? '' : selected.label }), _jsx(Icon, { name: "chevron-down", size: 16, style: { marginLeft: 'auto' } })] }), _jsx(Modal, { transparent: true, visible: isOpen, animationType: "fade", onRequestClose: () => setOpen(false), children: _jsx(DropdownWrapper, { onPress: () => setOpen(false), children: _jsx(DropdownContainer, { style: { maxHeight: dropdownContainerMaxHeight }, children: _jsxs(ScrollView, { nestedScrollEnabled: true, testID: `${testID}-OptionsScrollView`, children: [_jsxs(SelectOption, { accessible: true, accessibilityRole: "radio", onPress: () => handleOptionPress(requiredOption), children: [_jsx(StyledP, { children: _jsx(Strong, { children: requiredOption.label }) }), _jsx(Radio, { isChecked: selected.value === requiredOption.value, children: _jsx(RadioDot, { isChecked: selected.value === requiredOption.value }) })] }), Object.keys(optionsByCategories).map(category => (_jsxs(Fragment, { children: [category !== 'undefined' ? (_jsx(StyledCategory, { children: category })) : null, optionsByCategories[category].map((option, i) => (_jsxs(SelectOption, { accessible: true, accessibilityRole: "radio", isLastOption: i === optionsByCategories[category].length - 1, onPress: () => handleOptionPress(option), children: [_jsx(StyledP, { children: _jsx(Strong, { children: option.label }) }), _jsx(Radio, { isChecked: selected.value === option.value, children: _jsx(RadioDot, { isChecked: selected.value === option.value }) })] }, option.label)))] }, category)))] }) }) }) })] }));
|
|
93
94
|
};
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { jsx as _jsx, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
2
|
import { Field } from '../Field';
|
|
3
3
|
import { Select } from './Select';
|
|
4
|
-
export const SelectField = ({ error, options, onSelected, noOptionMessage, defaultSelected, testID, ...rest }) => (_jsx(Field, { affixWidth: 20, error: error, ...rest, children: _jsx(_Fragment, { children: _jsx(Select, { onSelected: onSelected, options: options, noOptionMessage: noOptionMessage, defaultSelected: defaultSelected, hasError: Boolean(error), testID: testID }) }) }));
|
|
4
|
+
export const SelectField = ({ error, options, onSelected, noOptionMessage, defaultSelected, testID, ref, ...rest }) => (_jsx(Field, { affixWidth: 20, error: error, ...rest, children: _jsx(_Fragment, { children: _jsx(Select, { onSelected: onSelected, options: options, noOptionMessage: noOptionMessage, defaultSelected: defaultSelected, hasError: Boolean(error), testID: testID, ref: ref }) }) }));
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
2
|
import { Field } from '../Field';
|
|
3
3
|
import { TextInput } from '../TextInput';
|
|
4
|
-
export const TextField = (props) => {
|
|
5
|
-
return (_jsx(Field, { ...props, children: _jsx(TextInput, {}) }));
|
|
4
|
+
export const TextField = ({ ref, ...props }) => {
|
|
5
|
+
return (_jsx(Field, { ...props, children: _jsx(TextInput, { ref: ref }) }));
|
|
6
6
|
};
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
2
|
import { Input } from '../Input/Input';
|
|
3
|
-
const TextInput = (props) => _jsx(Input, { ...props, keyboardType: "default", ref:
|
|
3
|
+
const TextInput = ({ ref, ...props }) => (_jsx(Input, { ...props, keyboardType: "default", ref: ref }));
|
|
4
4
|
export { TextInput };
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
2
|
import { Field } from '../Field';
|
|
3
3
|
import { TextareaInput } from '../TextareaInput';
|
|
4
|
-
export const TextareaField = ({ ...props }) => {
|
|
5
|
-
return (_jsx(Field, { ...props, children: _jsx(TextareaInput, {}) }));
|
|
4
|
+
export const TextareaField = ({ ref, ...props }) => {
|
|
5
|
+
return (_jsx(Field, { ...props, children: _jsx(TextareaInput, { ref: ref }) }));
|
|
6
6
|
};
|
|
@@ -16,7 +16,7 @@ export const StyledToggleInputWrapper = styled.View(({ theme, labelPosition }) =
|
|
|
16
16
|
? labelPosition === 'left'
|
|
17
17
|
? 'margin-left: 10px;'
|
|
18
18
|
: 'margin-right: 10px;'
|
|
19
|
-
:
|
|
19
|
+
: ''}
|
|
20
20
|
`;
|
|
21
21
|
});
|
|
22
22
|
export const StyledToggleInput = styled.View(({ theme, checked }) => {
|
|
@@ -36,6 +36,7 @@ export * from './PhoneInput';
|
|
|
36
36
|
export * from './Pictogram';
|
|
37
37
|
export * from './Radio';
|
|
38
38
|
export * from './RadioCard';
|
|
39
|
+
export * from './ScreenView';
|
|
39
40
|
export * from './RemoteImage';
|
|
40
41
|
export * from './SegmentedControls';
|
|
41
42
|
export * from './SelectField';
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
export * from './use-breakpoint';
|
|
1
|
+
export * from './use-breakpoint.native';
|
|
2
2
|
export * from './use-full-width';
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { useEffect, useState } from 'react';
|
|
2
|
-
import { useBreakpoint } from './use-breakpoint';
|
|
2
|
+
import { useBreakpoint } from './use-breakpoint.native';
|
|
3
3
|
export const useFullWidth = (fullWidth = 'small') => {
|
|
4
4
|
const [isFullWidth, setIsfullWidth] = useState(true);
|
|
5
5
|
const { smallAndUp } = useBreakpoint();
|
|
@@ -3,7 +3,7 @@ import { TouchableOpacityProps } from 'react-native';
|
|
|
3
3
|
import { IconName } from '../../providers/icons-types';
|
|
4
4
|
import { SizeSettings, StyledButtonWrapper } from './Button.styles';
|
|
5
5
|
export type ButtonVariantName = 'surface' | 'destructive' | 'outline' | 'outline-variant';
|
|
6
|
-
type ButtonBase = PropsWithChildren<TouchableOpacityProps & {
|
|
6
|
+
export type ButtonBase = PropsWithChildren<TouchableOpacityProps & {
|
|
7
7
|
variant?: ButtonVariantName;
|
|
8
8
|
inverted?: boolean;
|
|
9
9
|
size?: SizeSettings;
|
|
@@ -15,11 +15,12 @@ type ButtonWithText = ButtonBase & {
|
|
|
15
15
|
iconLeft?: IconName;
|
|
16
16
|
iconRight?: IconName;
|
|
17
17
|
};
|
|
18
|
-
type ButtonIconOnly = ButtonBase & {
|
|
18
|
+
export type ButtonIconOnly = ButtonBase & {
|
|
19
19
|
children?: never;
|
|
20
20
|
iconLeft?: IconName;
|
|
21
21
|
iconRight?: IconName;
|
|
22
22
|
};
|
|
23
|
+
export declare const DEFAULT_BUTTON_VARIANT = "surface";
|
|
23
24
|
export type ButtonProps = ButtonWithText | ButtonIconOnly;
|
|
24
25
|
declare const Button: ({ iconLeft, iconRight, children, fullWidth, variant, inverted, size, accessibilityRole, activeOpacity, ref, ...rest }: ButtonProps) => import("react/jsx-runtime").JSX.Element;
|
|
25
26
|
type OmittedButtonProps = Omit<ComponentProps<typeof Button>, 'variant' | 'children'>;
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
2
|
import { useBreakpoint } from '../../hooks';
|
|
3
3
|
import { StyledButtonIcon, StyledButtonText, StyledButtonWrapper, StyledInner, } from './Button.styles';
|
|
4
|
-
const
|
|
4
|
+
export const DEFAULT_BUTTON_VARIANT = 'surface';
|
|
5
|
+
const Button = ({ iconLeft, iconRight, children, fullWidth = false, variant = DEFAULT_BUTTON_VARIANT, inverted = false, size = 'default', accessibilityRole = 'button', activeOpacity = 0.8, ref, ...rest }) => {
|
|
5
6
|
const { smallAndUp } = useBreakpoint();
|
|
6
7
|
const isIconOnly = !children;
|
|
7
8
|
const iconSizes = {
|
|
@@ -94,7 +94,10 @@ const getBorderColor = (theme, variant, inverted) => {
|
|
|
94
94
|
if (variant === 'outline-variant') {
|
|
95
95
|
return button.surface.color.bgVariant;
|
|
96
96
|
}
|
|
97
|
-
|
|
97
|
+
if (inverted) {
|
|
98
|
+
return button.surface.color.bgInverted;
|
|
99
|
+
}
|
|
100
|
+
return button[variant].color.bg;
|
|
98
101
|
};
|
|
99
102
|
const getIconColor = (theme, inverted, variant) => {
|
|
100
103
|
const button = theme.button;
|
|
@@ -3443,7 +3443,7 @@ export declare const IconContainer: import("styled-components").StyledComponent<
|
|
|
3443
3443
|
}, {}, never>;
|
|
3444
3444
|
export declare const Metric: import("styled-components").StyledComponent<(props: import("react").PropsWithChildren<import("react-native").TextProps & Omit<{
|
|
3445
3445
|
inverted?: boolean;
|
|
3446
|
-
level: "
|
|
3446
|
+
level: import("../../Heading/Heading").HeadingLevel;
|
|
3447
3447
|
variant?: "brand" | "surface";
|
|
3448
3448
|
}, "level">>) => import("react/jsx-runtime").JSX.Element, {
|
|
3449
3449
|
color: {
|
|
@@ -4020,7 +4020,7 @@ export declare const Metric: import("styled-components").StyledComponent<(props:
|
|
|
4020
4020
|
}, {}, never>;
|
|
4021
4021
|
export declare const SubMetric: import("styled-components").StyledComponent<(props: import("react").PropsWithChildren<import("react-native").TextProps & Omit<{
|
|
4022
4022
|
inverted?: boolean;
|
|
4023
|
-
level: "
|
|
4023
|
+
level: import("../../Heading/Heading").HeadingLevel;
|
|
4024
4024
|
variant?: "brand" | "surface";
|
|
4025
4025
|
}, "level">>) => import("react/jsx-runtime").JSX.Element, {
|
|
4026
4026
|
color: {
|
|
@@ -2879,7 +2879,7 @@ export declare const ImageContent: import("styled-components").StyledComponent<t
|
|
|
2879
2879
|
}, {}, never>;
|
|
2880
2880
|
export declare const Title: import("styled-components").StyledComponent<(props: import("react").PropsWithChildren<import("react-native").TextProps & Omit<{
|
|
2881
2881
|
inverted?: boolean;
|
|
2882
|
-
level: "
|
|
2882
|
+
level: import("../../Heading/Heading").HeadingLevel;
|
|
2883
2883
|
variant?: "brand" | "surface";
|
|
2884
2884
|
}, "level">>) => import("react/jsx-runtime").JSX.Element, {
|
|
2885
2885
|
color: {
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { CurrencyInputProps } from '../CurrencyInput';
|
|
2
2
|
import { FieldProps } from '../Field';
|
|
3
3
|
type Props = Omit<FieldProps, 'children'> & CurrencyInputProps;
|
|
4
|
-
export declare const CurrencyField: ({ ...props }: Props) => import("react/jsx-runtime").JSX.Element;
|
|
4
|
+
export declare const CurrencyField: ({ ref, ...props }: Props) => import("react/jsx-runtime").JSX.Element;
|
|
5
5
|
export {};
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
2
|
import { CurrencyInput } from '../CurrencyInput';
|
|
3
3
|
import { Field } from '../Field';
|
|
4
|
-
export const CurrencyField = ({ ...props }) => {
|
|
5
|
-
return (_jsx(Field, { affixWidth: 40, ...props, children: _jsx(CurrencyInput, { ref:
|
|
4
|
+
export const CurrencyField = ({ ref, ...props }) => {
|
|
5
|
+
return (_jsx(Field, { affixWidth: 40, ...props, children: _jsx(CurrencyInput, { ref: ref }) }));
|
|
6
6
|
};
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { FieldProps } from '../Field';
|
|
2
2
|
import { InputProps } from '../Input/Input';
|
|
3
3
|
type Props = Omit<FieldProps, 'children'> & InputProps;
|
|
4
|
-
export declare const EmailField: ({ ...rest }: Props) => import("react/jsx-runtime").JSX.Element;
|
|
4
|
+
export declare const EmailField: ({ ref, ...rest }: Props) => import("react/jsx-runtime").JSX.Element;
|
|
5
5
|
export {};
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
2
|
import { EmailInput } from '../EmailInput';
|
|
3
3
|
import { Field } from '../Field';
|
|
4
|
-
export const EmailField = ({ ...rest }) => {
|
|
5
|
-
return (_jsx(Field, { ...rest, children: _jsx(EmailInput, {}) }));
|
|
4
|
+
export const EmailField = ({ ref, ...rest }) => {
|
|
5
|
+
return (_jsx(Field, { ...rest, children: _jsx(EmailInput, { ref: ref }) }));
|
|
6
6
|
};
|
|
@@ -1,25 +1,27 @@
|
|
|
1
1
|
import { numToPx } from '@ovotech/element-core';
|
|
2
2
|
import styled, { css } from '../../styled.native';
|
|
3
3
|
import { styledComponentWithBreakpoints } from '../../utils';
|
|
4
|
-
const StyledCol = styled.View(({ theme, span
|
|
4
|
+
const StyledCol = styled.View(({ theme, span, xsmallAndUp, small, smallAndUp, medium, mediumAndUp }) => {
|
|
5
5
|
const COLS = 12;
|
|
6
|
-
const gutter = mediumAndUp ? theme.space[
|
|
7
|
-
const percentage = (span / COLS) * 100;
|
|
6
|
+
const gutter = mediumAndUp ? theme.space[600] : theme.space[400];
|
|
7
|
+
const percentage = span ? (span / COLS) * 100 : 100;
|
|
8
8
|
const smallPercentage = small ? (small / COLS) * 100 : percentage;
|
|
9
9
|
const mediumPercentage = medium ? (medium / COLS) * 100 : smallPercentage;
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
10
|
+
let maxWidth;
|
|
11
|
+
if (mediumAndUp) {
|
|
12
|
+
maxWidth = mediumPercentage;
|
|
13
|
+
}
|
|
14
|
+
else if (smallAndUp || xsmallAndUp) {
|
|
15
|
+
maxWidth = span ? 50 : 100;
|
|
16
|
+
}
|
|
17
|
+
else {
|
|
18
|
+
maxWidth = 100;
|
|
19
|
+
}
|
|
18
20
|
return css `
|
|
19
21
|
flex: 0 0 auto;
|
|
20
22
|
padding-left: ${numToPx(gutter / 2)};
|
|
21
23
|
padding-right: ${numToPx(gutter / 2)};
|
|
22
|
-
margin-bottom: ${numToPx(
|
|
24
|
+
margin-bottom: ${numToPx(theme.space[smallAndUp ? 800 : 600])};
|
|
23
25
|
max-width: ${maxWidth}%;
|
|
24
26
|
width: 100%;
|
|
25
27
|
`;
|
|
@@ -1,23 +1,19 @@
|
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
-
import { numToPx } from '
|
|
2
|
+
import { numToPx } from '../..';
|
|
3
3
|
import styled, { css } from '../../styled.native';
|
|
4
4
|
import { styledComponentWithBreakpoints } from '../../utils';
|
|
5
5
|
const StyledRow = styled.View(({ theme, isNested, smallAndUp, mediumAndUp }) => {
|
|
6
|
-
const
|
|
7
|
-
const
|
|
8
|
-
/* We need to make up for the half gutter that is added to the left and right of a column, between the small and medium breakpoints */
|
|
9
|
-
const additionalMargin = smallAndUp ? (margin - gutter) / 2 : 0;
|
|
6
|
+
const rowGap = mediumAndUp || smallAndUp ? theme.space[800] : theme.space[600];
|
|
7
|
+
const colGap = mediumAndUp ? theme.space[600] : theme.space[400];
|
|
10
8
|
return css `
|
|
11
|
-
padding-left: ${numToPx(margin / 2 + additionalMargin)};
|
|
12
|
-
padding-right: ${numToPx(margin / 2 + additionalMargin)};
|
|
13
9
|
margin: 0 auto;
|
|
14
|
-
max-width: ${theme.breakpoint.large +
|
|
10
|
+
max-width: ${theme.breakpoint.large + rowGap}px;
|
|
15
11
|
width: 100%;
|
|
16
12
|
|
|
17
13
|
${isNested
|
|
18
14
|
? `
|
|
19
|
-
margin-left: -${numToPx(
|
|
20
|
-
margin-right: -${numToPx(
|
|
15
|
+
margin-left: -${numToPx(colGap / 2)};
|
|
16
|
+
margin-right: -${numToPx(colGap / 2)};
|
|
21
17
|
width: auto;
|
|
22
18
|
max-width: 200%; /* max width none not supported in RN */
|
|
23
19
|
`
|
|
@@ -1,10 +1,12 @@
|
|
|
1
1
|
import { PropsWithChildren } from 'react';
|
|
2
2
|
import { TextProps } from 'react-native';
|
|
3
|
+
export type HeadingLevel = 'xl' | '2xl' | '3xl' | '4xl';
|
|
3
4
|
type HeadingProps = {
|
|
4
5
|
inverted?: boolean;
|
|
5
|
-
level:
|
|
6
|
+
level: HeadingLevel;
|
|
6
7
|
variant?: 'brand' | 'surface';
|
|
7
8
|
};
|
|
9
|
+
export declare const Heading: ({ accessibilityRole, ...rest }: PropsWithChildren<TextProps & HeadingProps>) => import("react/jsx-runtime").JSX.Element;
|
|
8
10
|
export declare const Heading1: (props: PropsWithChildren<TextProps & Omit<HeadingProps, "level">>) => import("react/jsx-runtime").JSX.Element;
|
|
9
11
|
export declare const Heading2: (props: PropsWithChildren<TextProps & Omit<HeadingProps, "level">>) => import("react/jsx-runtime").JSX.Element;
|
|
10
12
|
export declare const Heading3: (props: PropsWithChildren<TextProps & Omit<HeadingProps, "level">>) => import("react/jsx-runtime").JSX.Element;
|
|
@@ -21,7 +21,7 @@ const StyledHeading = styled.Text(({ theme, smallAndUp, inverted, level, variant
|
|
|
21
21
|
color: ${color};
|
|
22
22
|
`;
|
|
23
23
|
});
|
|
24
|
-
const Heading = ({ accessibilityRole = 'header', ...rest }) => {
|
|
24
|
+
export const Heading = ({ accessibilityRole = 'header', ...rest }) => {
|
|
25
25
|
const breakpoints = useBreakpoint();
|
|
26
26
|
return (_jsx(StyledHeading, { accessible: true, accessibilityRole: accessibilityRole, ...breakpoints, ...rest }));
|
|
27
27
|
};
|
|
@@ -1,24 +1,27 @@
|
|
|
1
|
-
import {
|
|
2
|
-
export type
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
accessibilityHint?: string;
|
|
1
|
+
import { IconName } from '../../providers';
|
|
2
|
+
export type Layer = 0 | 1 | 2 | 3 | 4;
|
|
3
|
+
type ActionButton = {
|
|
4
|
+
icon?: IconName;
|
|
5
|
+
onPress: () => void;
|
|
7
6
|
};
|
|
8
|
-
|
|
7
|
+
type StepCounterProps = {
|
|
8
|
+
totalSteps: number;
|
|
9
|
+
currentStep: number;
|
|
10
|
+
};
|
|
11
|
+
export type ScrollState = 'initial' | 'scrollStart' | 'scrolling' | 'scrollBack';
|
|
12
|
+
export type NavHeaderProps<L extends Layer> = {
|
|
13
|
+
layer: L;
|
|
9
14
|
title?: string;
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
* @param height - height of the expanded NavHeader
|
|
21
|
-
*/
|
|
22
|
-
onHeaderHeightChange?: (height: number) => void;
|
|
15
|
+
actionButtons?: L extends 0 | 1 ? {
|
|
16
|
+
account?: ActionButton;
|
|
17
|
+
help?: ActionButton;
|
|
18
|
+
} : {
|
|
19
|
+
help?: ActionButton;
|
|
20
|
+
};
|
|
21
|
+
onBackPress?: () => void;
|
|
22
|
+
stepCounter?: StepCounterProps;
|
|
23
|
+
scrollState: ScrollState;
|
|
24
|
+
loading?: boolean;
|
|
23
25
|
};
|
|
24
|
-
export declare const NavHeader: ({
|
|
26
|
+
export declare const NavHeader: <L extends Layer>({ layer, onBackPress, actionButtons, title, stepCounter, scrollState, loading, }: NavHeaderProps<L>) => import("react/jsx-runtime").JSX.Element;
|
|
27
|
+
export {};
|
|
@@ -1,33 +1,130 @@
|
|
|
1
|
-
import { jsx as _jsx,
|
|
2
|
-
import
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
2
|
+
import { useEffect, useMemo } from 'react';
|
|
3
|
+
import { Platform } from 'react-native';
|
|
4
|
+
import { ComplexAnimationBuilder, Easing, FadeInUp, LinearTransition, useAnimatedStyle, useSharedValue, withTiming, } from 'react-native-reanimated';
|
|
5
|
+
import { useBreakpoint } from '../../hooks';
|
|
6
|
+
import { Heading, Heading2, Heading3, Heading4, } from '../Heading/Heading';
|
|
7
|
+
import { P } from '../P';
|
|
8
|
+
import { Strong } from '../Strong';
|
|
9
|
+
import { HeaderContainer, NavBackButton, NavContainer, ShadowContainer, SideContainer, SkeletonNavHeading, TitleContainer, } from './NavHeader.styles';
|
|
10
|
+
import { ActionButtons } from './NavHeaderComponents/ActionButtons';
|
|
11
|
+
import { StepCounterBars } from './NavHeaderComponents/StepCounterBars';
|
|
12
|
+
import { getTitleLength } from './utils';
|
|
13
|
+
const baseStyle = {
|
|
14
|
+
hasDropShadow: false,
|
|
15
|
+
isCollapsed: false,
|
|
16
|
+
};
|
|
17
|
+
const hasDropShadowOnly = {
|
|
18
|
+
hasDropShadow: true,
|
|
19
|
+
isCollapsed: false,
|
|
20
|
+
};
|
|
21
|
+
const isCollapsedAndDropShadow = {
|
|
22
|
+
hasDropShadow: true,
|
|
23
|
+
isCollapsed: true,
|
|
24
|
+
};
|
|
25
|
+
const scrollStyleMap = {
|
|
26
|
+
0: {
|
|
27
|
+
initial: baseStyle,
|
|
28
|
+
scrollStart: baseStyle,
|
|
29
|
+
scrolling: isCollapsedAndDropShadow,
|
|
30
|
+
scrollBack: hasDropShadowOnly,
|
|
31
|
+
},
|
|
32
|
+
1: {
|
|
33
|
+
initial: baseStyle,
|
|
34
|
+
scrollStart: hasDropShadowOnly,
|
|
35
|
+
scrolling: isCollapsedAndDropShadow,
|
|
36
|
+
scrollBack: hasDropShadowOnly,
|
|
37
|
+
},
|
|
38
|
+
2: {
|
|
39
|
+
initial: hasDropShadowOnly,
|
|
40
|
+
scrollStart: hasDropShadowOnly,
|
|
41
|
+
scrolling: hasDropShadowOnly,
|
|
42
|
+
scrollBack: hasDropShadowOnly,
|
|
43
|
+
},
|
|
44
|
+
};
|
|
45
|
+
const LayerHeadingMap = {
|
|
46
|
+
0: '3xl',
|
|
47
|
+
1: '2xl',
|
|
48
|
+
2: 'xl',
|
|
49
|
+
3: 'xl',
|
|
50
|
+
4: 'xl',
|
|
51
|
+
};
|
|
52
|
+
const ANIMATION_DURATION = 300;
|
|
53
|
+
export const NavHeader = ({ layer, onBackPress, actionButtons, title, stepCounter, scrollState, loading = false, }) => {
|
|
54
|
+
const displayTitle = getTitleLength({ layer, title });
|
|
55
|
+
const platform = Platform.OS;
|
|
56
|
+
const titleIsCentreAligned = layer > 1 && platform === 'ios';
|
|
57
|
+
const { isCollapsed, hasDropShadow } = scrollStyleMap[Math.min(layer, 2)][scrollState];
|
|
58
|
+
const shadowOpacity = useSharedValue(0.5);
|
|
59
|
+
const elevation = useSharedValue(9);
|
|
60
|
+
const LT = LinearTransition.duration(ANIMATION_DURATION);
|
|
61
|
+
const FADE_IN_DISTANCE = layer === 0 ? -68 : -50;
|
|
62
|
+
const FADE_OUT_DISTANCE = layer === 0 ? -72 : -52;
|
|
63
|
+
const ExitAnimation = useMemo(() => {
|
|
64
|
+
var _a;
|
|
65
|
+
return _a = class FadeOutUp extends ComplexAnimationBuilder {
|
|
66
|
+
constructor() {
|
|
67
|
+
super(...arguments);
|
|
68
|
+
this.build = () => {
|
|
69
|
+
const delayFunction = this.getDelayFunction();
|
|
70
|
+
const [animation, config] = this.getAnimationAndConfig();
|
|
71
|
+
const callback = this.callbackV;
|
|
72
|
+
const initialValues = this.initialValues;
|
|
73
|
+
const delay = this.getDelay();
|
|
74
|
+
return () => {
|
|
75
|
+
'worklet';
|
|
76
|
+
return {
|
|
77
|
+
animations: {
|
|
78
|
+
opacity: delayFunction(delay, animation(0, config)),
|
|
79
|
+
transform: [
|
|
80
|
+
{
|
|
81
|
+
translateY: delayFunction(delay, animation(FADE_OUT_DISTANCE, config)),
|
|
82
|
+
},
|
|
83
|
+
],
|
|
84
|
+
},
|
|
85
|
+
initialValues: {
|
|
86
|
+
opacity: 1,
|
|
87
|
+
transform: [{ translateY: 0 }],
|
|
88
|
+
...initialValues,
|
|
89
|
+
},
|
|
90
|
+
callback,
|
|
91
|
+
};
|
|
92
|
+
};
|
|
93
|
+
};
|
|
94
|
+
}
|
|
95
|
+
static createInstance() {
|
|
96
|
+
return new _a();
|
|
97
|
+
}
|
|
98
|
+
},
|
|
99
|
+
_a.presetName = 'FadeOutUp',
|
|
100
|
+
_a;
|
|
101
|
+
}, [layer]);
|
|
102
|
+
const FadingAnimation = {
|
|
103
|
+
Enter: FadeInUp.duration(ANIMATION_DURATION)
|
|
104
|
+
.easing(Easing.ease)
|
|
105
|
+
.withInitialValues({ transform: [{ translateY: FADE_IN_DISTANCE }] }),
|
|
106
|
+
Exit: ExitAnimation.duration(ANIMATION_DURATION).easing(Easing.linear),
|
|
107
|
+
};
|
|
108
|
+
useEffect(() => {
|
|
109
|
+
shadowOpacity.value = withTiming(hasDropShadow ? 0.5 : 0, {
|
|
110
|
+
duration: ANIMATION_DURATION,
|
|
111
|
+
easing: Easing.ease,
|
|
112
|
+
});
|
|
113
|
+
elevation.value = withTiming(hasDropShadow ? 9 : 0, {
|
|
114
|
+
duration: ANIMATION_DURATION,
|
|
115
|
+
easing: Easing.ease,
|
|
116
|
+
});
|
|
117
|
+
}, [scrollState, shadowOpacity, hasDropShadow, elevation, isCollapsed]);
|
|
118
|
+
const animatedShadowStyle = useAnimatedStyle(() => {
|
|
12
119
|
return {
|
|
13
|
-
|
|
120
|
+
shadowOpacity: shadowOpacity.value,
|
|
121
|
+
elevation: elevation.value,
|
|
14
122
|
};
|
|
15
123
|
});
|
|
16
|
-
const
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
if (!scrolled) {
|
|
23
|
-
onHeaderHeightChange?.(height);
|
|
24
|
-
}
|
|
25
|
-
layoutHeight.value = withTiming(height, {
|
|
26
|
-
duration: FADE_ANIMATION_DURATION,
|
|
27
|
-
easing: Easing.linear,
|
|
28
|
-
});
|
|
29
|
-
};
|
|
30
|
-
// NavWrapper will recieve height of the NavContainer and animate it
|
|
31
|
-
// content inside NavContainer is the only dynamic part of NavHeader
|
|
32
|
-
return (_jsx(NavWrapper, { collapsed: scrolled, style: animatedHeightStyle, children: _jsxs(NavContainer, { topOffset: topOffset, hasTitle: hasTitle, onLayout: onLayout, children: [_jsx(BackActionWrapper, { collapsed: scrolled, hasBackButton: canGoBack, children: canGoBack && (_jsx(Action, { standalone: true, iconLeft: "chevron-left-small", onPress: onBackButtonPress, children: backButtonText })) }), scrolled ? (_jsxs(_Fragment, { children: [_jsx(CollapsedTitleWrapper, { entering: FadeInDown.delay(FADE_ANIMATION_DURATION), exiting: FadeOutDown.duration(FADE_ANIMATION_DURATION), children: _jsx(CollapsedTitle, { numberOfLines: 1, ellipsizeMode: "tail", children: title }) }), _jsx(HeaderGap, { hasRightAction: hasRightAction }), hasRightAction && (_jsx(_Fragment, { children: _jsx(Animated.View, { entering: FadeInDown.delay(FADE_ANIMATION_DURATION), exiting: FadeOutDown.duration(FADE_ANIMATION_DURATION), accessibilityRole: "button", accessibilityLabel: rightActionConfig?.accessibilityLabel, accessibilityHint: rightActionConfig?.accessibilityHint, children: _jsx(Button, { iconRight: rightActionConfig.iconName, onPress: rightActionConfig.onActionPress }) }) }))] })) : (_jsxs(_Fragment, { children: [_jsx(ExpandedTitle, { hasRightAction: !hasRightAction, hasTitle: hasTitle, numberOfLines: 2, ellipsizeMode: "tail", hasBackButton: canGoBack, entering: FadeInUp.delay(FADE_ANIMATION_DURATION), exiting: FadeOutUp.duration(FADE_ANIMATION_DURATION), children: title }), hasRightAction && (_jsx(Animated.View, { entering: FadeInUp.delay(FADE_ANIMATION_DURATION), exiting: FadeOutUp.duration(FADE_ANIMATION_DURATION), accessibilityRole: "button", accessibilityLabel: rightActionConfig?.accessibilityLabel, accessibilityHint: rightActionConfig?.accessibilityHint, children: _jsx(Button, { iconRight: rightActionConfig.iconName, onPress: rightActionConfig.onActionPress }) }))] }))] }) }));
|
|
124
|
+
const breakpoints = useBreakpoint();
|
|
125
|
+
return (_jsx(ShadowContainer, { style: [animatedShadowStyle], children: _jsx(NavContainer, { breakpoints: breakpoints, layer: layer, layout: LT, isCollapsed: isCollapsed, children: !isCollapsed && (_jsxs(_Fragment, { children: [_jsxs(HeaderContainer, { layout: LT, entering: FadingAnimation.Enter, exiting: FadingAnimation.Exit, children: [_jsx(SideContainer, { flex: titleIsCentreAligned ? 1 : 0, side: "start", children: layer > 1 && (_jsx(NavBackButton, { onPress: () => {
|
|
126
|
+
onBackPress && onBackPress();
|
|
127
|
+
}, variant: "bright", iconLeft: platform === 'ios' ? 'chevron-left' : 'arrow-left' })) }), _jsxs(TitleContainer, { layer: layer, isIOS: platform === 'ios', children: [loading ? (_jsx(SkeletonNavHeading, { size: "100%", headingComponent: layer === 0 ? Heading2 : layer === 1 ? Heading3 : Heading4 })) : layer < 2 ? (_jsx(Heading, { inverted: layer < 2, level: LayerHeadingMap[layer], children: displayTitle })) : (_jsx(P, { size: "md", children: _jsx(Strong, { maxLength: 23, children: displayTitle }) })), stepCounter && !loading && (_jsx(P, { size: "sm", children: `Step ${stepCounter.currentStep <= stepCounter.totalSteps
|
|
128
|
+
? stepCounter.currentStep
|
|
129
|
+
: stepCounter.totalSteps} of ${stepCounter.totalSteps}` }))] }), _jsx(SideContainer, { side: "end", children: actionButtons && (_jsx(ActionButtons, { loading: loading, layer: layer, actionButtons: actionButtons })) })] }), stepCounter && (_jsx(StepCounterBars, { loading: loading, totalSteps: stepCounter.totalSteps, currentStep: stepCounter.currentStep }))] })) }) }));
|
|
33
130
|
};
|