@planningcenter/chat-react-native 1.4.2-rc.0 → 1.4.2-rc.2
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/build/components/display/avatar.d.ts +10 -0
- package/build/components/display/avatar.d.ts.map +1 -0
- package/build/components/display/avatar.js +11 -0
- package/build/components/display/avatar.js.map +1 -0
- package/build/components/display/avatar_group.d.ts +9 -0
- package/build/components/display/avatar_group.d.ts.map +1 -0
- package/build/components/display/avatar_group.js +11 -0
- package/build/components/display/avatar_group.js.map +1 -0
- package/build/components/display/heading.d.ts +8 -0
- package/build/components/display/heading.d.ts.map +1 -0
- package/build/components/display/heading.js +53 -0
- package/build/components/display/heading.js.map +1 -0
- package/build/components/display/image.d.ts +10 -3
- package/build/components/display/image.d.ts.map +1 -1
- package/build/components/display/image.js +7 -5
- package/build/components/display/image.js.map +1 -1
- package/build/components/display/index.d.ts +4 -1
- package/build/components/display/index.d.ts.map +1 -1
- package/build/components/display/index.js +4 -1
- package/build/components/display/index.js.map +1 -1
- package/build/components/display/text.d.ts +1 -1
- package/build/components/display/text.d.ts.map +1 -1
- package/build/components/display/text.js +7 -6
- package/build/components/display/text.js.map +1 -1
- package/build/components/primitive/avatar_primitive.d.ts +39 -0
- package/build/components/primitive/avatar_primitive.d.ts.map +1 -0
- package/build/components/primitive/avatar_primitive.js +204 -0
- package/build/components/primitive/avatar_primitive.js.map +1 -0
- package/build/contexts/chat_context.js +2 -2
- package/build/contexts/chat_context.js.map +1 -1
- package/build/screens/display.d.ts.map +1 -1
- package/build/screens/display.js +46 -6
- package/build/screens/display.js.map +1 -1
- package/build/utils/platform_styles.d.ts +2 -0
- package/build/utils/platform_styles.d.ts.map +1 -0
- package/build/utils/platform_styles.js +7 -0
- package/build/utils/platform_styles.js.map +1 -0
- package/build/utils/theme.d.ts +2 -2
- package/build/utils/theme.d.ts.map +1 -1
- package/build/utils/theme.js +2 -2
- package/build/utils/theme.js.map +1 -1
- package/build/vendor/tapestry/alias_tokens_color_map.d.ts +55 -0
- package/build/vendor/tapestry/alias_tokens_color_map.d.ts.map +1 -0
- package/build/vendor/tapestry/{tapestry_alias_tokens_color_map.js → alias_tokens_color_map.js} +4 -2
- package/build/vendor/tapestry/alias_tokens_color_map.js.map +1 -0
- package/build/vendor/tapestry/tokens.d.ts +49 -35
- package/build/vendor/tapestry/tokens.d.ts.map +1 -1
- package/build/vendor/tapestry/tokens.js +18 -0
- package/build/vendor/tapestry/tokens.js.map +1 -1
- package/package.json +6 -10
- package/src/__mocks__/@react-native-async-storage/async-storage.js +3 -0
- package/src/__mocks__/react-native-device-info.js +3 -0
- package/src/__tests__/hooks/useTheme.tsx +37 -0
- package/src/components/display/avatar.tsx +23 -0
- package/src/components/display/avatar_group.tsx +21 -0
- package/src/components/display/heading.tsx +71 -0
- package/src/components/display/image.tsx +20 -8
- package/src/components/display/index.ts +4 -1
- package/src/components/display/text.tsx +7 -6
- package/src/components/primitive/avatar_primitive.tsx +374 -0
- package/src/contexts/chat_context.tsx +2 -2
- package/src/screens/display.tsx +47 -9
- package/src/utils/platform_styles.ts +7 -0
- package/src/utils/theme.ts +3 -3
- package/src/vendor/tapestry/{tapestry_alias_tokens_color_map.ts → alias_tokens_color_map.ts} +8 -5
- package/src/vendor/tapestry/tokens.ts +25 -50
- package/build/vendor/tapestry/tapestry_alias_tokens_color_map.d.ts +0 -53
- package/build/vendor/tapestry/tapestry_alias_tokens_color_map.d.ts.map +0 -1
- package/build/vendor/tapestry/tapestry_alias_tokens_color_map.js.map +0 -1
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { type AvatarImageProps, type AvatarPresenceProps, type AvatarRootProps } from '../primitive/avatar_primitive';
|
|
3
|
+
interface AvatarProps {
|
|
4
|
+
sourceUri: AvatarImageProps['sourceUri'];
|
|
5
|
+
size?: AvatarRootProps['size'];
|
|
6
|
+
presence?: AvatarPresenceProps['presence'];
|
|
7
|
+
}
|
|
8
|
+
export declare function Avatar({ presence, size, sourceUri }: AvatarProps): React.JSX.Element;
|
|
9
|
+
export {};
|
|
10
|
+
//# sourceMappingURL=avatar.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"avatar.d.ts","sourceRoot":"","sources":["../../../src/components/display/avatar.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAwB,EACtB,KAAK,gBAAgB,EACrB,KAAK,mBAAmB,EACxB,KAAK,eAAe,EACrB,MAAM,+BAA+B,CAAA;AAEtC,UAAU,WAAW;IACnB,SAAS,EAAE,gBAAgB,CAAC,WAAW,CAAC,CAAA;IACxC,IAAI,CAAC,EAAE,eAAe,CAAC,MAAM,CAAC,CAAA;IAC9B,QAAQ,CAAC,EAAE,mBAAmB,CAAC,UAAU,CAAC,CAAA;CAC3C;AAED,wBAAgB,MAAM,CAAC,EAAE,QAAQ,EAAE,IAAW,EAAE,SAAS,EAAE,EAAE,WAAW,qBASvE"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import AvatarPrimitive from '../primitive/avatar_primitive';
|
|
3
|
+
export function Avatar({ presence, size = 'lg', sourceUri }) {
|
|
4
|
+
return (<AvatarPrimitive.Root size={size}>
|
|
5
|
+
<AvatarPrimitive.Mask>
|
|
6
|
+
<AvatarPrimitive.Image sourceUri={sourceUri}/>
|
|
7
|
+
</AvatarPrimitive.Mask>
|
|
8
|
+
{presence && <AvatarPrimitive.Presence presence={presence}/>}
|
|
9
|
+
</AvatarPrimitive.Root>);
|
|
10
|
+
}
|
|
11
|
+
//# sourceMappingURL=avatar.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"avatar.js","sourceRoot":"","sources":["../../../src/components/display/avatar.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,eAIN,MAAM,+BAA+B,CAAA;AAQtC,MAAM,UAAU,MAAM,CAAC,EAAE,QAAQ,EAAE,IAAI,GAAG,IAAI,EAAE,SAAS,EAAe;IACtE,OAAO,CACL,CAAC,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,CAC/B;MAAA,CAAC,eAAe,CAAC,IAAI,CACnB;QAAA,CAAC,eAAe,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC,SAAS,CAAC,EAC9C;MAAA,EAAE,eAAe,CAAC,IAAI,CACtB;MAAA,CAAC,QAAQ,IAAI,CAAC,eAAe,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC,QAAQ,CAAC,EAAG,CAC/D;IAAA,EAAE,eAAe,CAAC,IAAI,CAAC,CACxB,CAAA;AACH,CAAC","sourcesContent":["import React from 'react'\nimport AvatarPrimitive, {\n type AvatarImageProps,\n type AvatarPresenceProps,\n type AvatarRootProps,\n} from '../primitive/avatar_primitive'\n\ninterface AvatarProps {\n sourceUri: AvatarImageProps['sourceUri']\n size?: AvatarRootProps['size']\n presence?: AvatarPresenceProps['presence']\n}\n\nexport function Avatar({ presence, size = 'lg', sourceUri }: AvatarProps) {\n return (\n <AvatarPrimitive.Root size={size}>\n <AvatarPrimitive.Mask>\n <AvatarPrimitive.Image sourceUri={sourceUri} />\n </AvatarPrimitive.Mask>\n {presence && <AvatarPrimitive.Presence presence={presence} />}\n </AvatarPrimitive.Root>\n )\n}\n"]}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { type AvatarGroupProps, type AvatarRootProps } from '../primitive/avatar_primitive';
|
|
3
|
+
interface AvatarGroupDisplayProps {
|
|
4
|
+
sourceUris: AvatarGroupProps['sourceUris'];
|
|
5
|
+
size?: AvatarRootProps['size'];
|
|
6
|
+
}
|
|
7
|
+
export declare function AvatarGroup({ sourceUris, size }: AvatarGroupDisplayProps): React.JSX.Element;
|
|
8
|
+
export {};
|
|
9
|
+
//# sourceMappingURL=avatar_group.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"avatar_group.d.ts","sourceRoot":"","sources":["../../../src/components/display/avatar_group.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAwB,EACtB,KAAK,gBAAgB,EACrB,KAAK,eAAe,EACrB,MAAM,+BAA+B,CAAA;AAEtC,UAAU,uBAAuB;IAC/B,UAAU,EAAE,gBAAgB,CAAC,YAAY,CAAC,CAAA;IAC1C,IAAI,CAAC,EAAE,eAAe,CAAC,MAAM,CAAC,CAAA;CAC/B;AAED,wBAAgB,WAAW,CAAC,EAAE,UAAU,EAAE,IAAW,EAAE,EAAE,uBAAuB,qBAS/E"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import AvatarPrimitive from '../primitive/avatar_primitive';
|
|
3
|
+
export function AvatarGroup({ sourceUris, size = 'lg' }) {
|
|
4
|
+
return (<AvatarPrimitive.Root size={size}>
|
|
5
|
+
<AvatarPrimitive.Mask>
|
|
6
|
+
<AvatarPrimitive.Group sourceUris={sourceUris}/>
|
|
7
|
+
<AvatarPrimitive.GroupLoader />
|
|
8
|
+
</AvatarPrimitive.Mask>
|
|
9
|
+
</AvatarPrimitive.Root>);
|
|
10
|
+
}
|
|
11
|
+
//# sourceMappingURL=avatar_group.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"avatar_group.js","sourceRoot":"","sources":["../../../src/components/display/avatar_group.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,eAGN,MAAM,+BAA+B,CAAA;AAOtC,MAAM,UAAU,WAAW,CAAC,EAAE,UAAU,EAAE,IAAI,GAAG,IAAI,EAA2B;IAC9E,OAAO,CACL,CAAC,eAAe,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,CAC/B;MAAA,CAAC,eAAe,CAAC,IAAI,CACnB;QAAA,CAAC,eAAe,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC,UAAU,CAAC,EAC9C;QAAA,CAAC,eAAe,CAAC,WAAW,CAAC,AAAD,EAC9B;MAAA,EAAE,eAAe,CAAC,IAAI,CACxB;IAAA,EAAE,eAAe,CAAC,IAAI,CAAC,CACxB,CAAA;AACH,CAAC","sourcesContent":["import React from 'react'\nimport AvatarPrimitive, {\n type AvatarGroupProps,\n type AvatarRootProps,\n} from '../primitive/avatar_primitive'\n\ninterface AvatarGroupDisplayProps {\n sourceUris: AvatarGroupProps['sourceUris']\n size?: AvatarRootProps['size']\n}\n\nexport function AvatarGroup({ sourceUris, size = 'lg' }: AvatarGroupDisplayProps) {\n return (\n <AvatarPrimitive.Root size={size}>\n <AvatarPrimitive.Mask>\n <AvatarPrimitive.Group sourceUris={sourceUris} />\n <AvatarPrimitive.GroupLoader />\n </AvatarPrimitive.Mask>\n </AvatarPrimitive.Root>\n )\n}\n"]}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { TextProps as ReactNativeTextProps } from 'react-native';
|
|
3
|
+
interface TextProps extends ReactNativeTextProps {
|
|
4
|
+
variant?: 'h1' | 'h2' | 'h3' | 'h4';
|
|
5
|
+
}
|
|
6
|
+
export declare function Heading({ style, variant, children, ...props }: TextProps): React.JSX.Element;
|
|
7
|
+
export {};
|
|
8
|
+
//# sourceMappingURL=heading.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"heading.d.ts","sourceRoot":"","sources":["../../../src/components/display/heading.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,EAIL,SAAS,IAAI,oBAAoB,EAClC,MAAM,cAAc,CAAA;AAIrB,UAAU,SAAU,SAAQ,oBAAoB;IAC9C,OAAO,CAAC,EAAE,IAAI,GAAG,IAAI,GAAG,IAAI,GAAG,IAAI,CAAA;CACpC;AAED,wBAAgB,OAAO,CAAC,EAAE,KAAK,EAAE,OAAc,EAAE,QAAQ,EAAE,GAAG,KAAK,EAAE,EAAE,SAAS,qBAkB/E"}
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
import { useTheme } from '../../hooks';
|
|
2
|
+
import React from 'react';
|
|
3
|
+
import { Platform, StyleSheet, Text as ReactNativeText, } from 'react-native';
|
|
4
|
+
import { tokens } from '../../vendor/tapestry/tokens';
|
|
5
|
+
import { platformFontWeightBold } from '../../utils/platform_styles';
|
|
6
|
+
export function Heading({ style, variant = 'h1', children, ...props }) {
|
|
7
|
+
const styles = useStyles();
|
|
8
|
+
const variantStyleMap = {
|
|
9
|
+
h1: styles.heading1,
|
|
10
|
+
h2: styles.heading2,
|
|
11
|
+
h3: styles.heading3,
|
|
12
|
+
h4: styles.heading4,
|
|
13
|
+
};
|
|
14
|
+
return (<ReactNativeText style={[styles.global, variantStyleMap[variant], style]} accessibilityRole="header" {...props}>
|
|
15
|
+
{children}
|
|
16
|
+
</ReactNativeText>);
|
|
17
|
+
}
|
|
18
|
+
const useStyles = () => {
|
|
19
|
+
const { colors } = useTheme();
|
|
20
|
+
return StyleSheet.create({
|
|
21
|
+
global: {
|
|
22
|
+
fontFamily: Platform.select({
|
|
23
|
+
ios: 'System',
|
|
24
|
+
android: 'normal',
|
|
25
|
+
}),
|
|
26
|
+
},
|
|
27
|
+
heading1: {
|
|
28
|
+
color: colors.textColorDefaultHeadline,
|
|
29
|
+
fontSize: 25, // Todo: Check with UX on correct token
|
|
30
|
+
lineHeight: 32,
|
|
31
|
+
},
|
|
32
|
+
heading2: {
|
|
33
|
+
color: colors.textColorDefaultHeadline,
|
|
34
|
+
fontWeight: platformFontWeightBold,
|
|
35
|
+
fontSize: 21, // Todo: Check with UX on correct token
|
|
36
|
+
lineHeight: 24,
|
|
37
|
+
},
|
|
38
|
+
heading3: {
|
|
39
|
+
color: colors.textColorDefaultHeadline,
|
|
40
|
+
fontWeight: platformFontWeightBold,
|
|
41
|
+
fontSize: tokens.fontSizeLg,
|
|
42
|
+
lineHeight: 22,
|
|
43
|
+
},
|
|
44
|
+
heading4: {
|
|
45
|
+
color: colors.textColorDefaultSecondary,
|
|
46
|
+
fontWeight: platformFontWeightBold,
|
|
47
|
+
fontSize: tokens.fontSizeSm,
|
|
48
|
+
lineHeight: 20,
|
|
49
|
+
textTransform: 'uppercase',
|
|
50
|
+
},
|
|
51
|
+
});
|
|
52
|
+
};
|
|
53
|
+
//# sourceMappingURL=heading.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"heading.js","sourceRoot":"","sources":["../../../src/components/display/heading.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAA;AACtC,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,EACL,QAAQ,EACR,UAAU,EACV,IAAI,IAAI,eAAe,GAExB,MAAM,cAAc,CAAA;AACrB,OAAO,EAAE,MAAM,EAAE,MAAM,8BAA8B,CAAA;AACrD,OAAO,EAAE,sBAAsB,EAAE,MAAM,6BAA6B,CAAA;AAMpE,MAAM,UAAU,OAAO,CAAC,EAAE,KAAK,EAAE,OAAO,GAAG,IAAI,EAAE,QAAQ,EAAE,GAAG,KAAK,EAAa;IAC9E,MAAM,MAAM,GAAG,SAAS,EAAE,CAAA;IAC1B,MAAM,eAAe,GAAG;QACtB,EAAE,EAAE,MAAM,CAAC,QAAQ;QACnB,EAAE,EAAE,MAAM,CAAC,QAAQ;QACnB,EAAE,EAAE,MAAM,CAAC,QAAQ;QACnB,EAAE,EAAE,MAAM,CAAC,QAAQ;KACpB,CAAA;IAED,OAAO,CACL,CAAC,eAAe,CACd,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,MAAM,EAAE,eAAe,CAAC,OAAO,CAAC,EAAE,KAAK,CAAC,CAAC,CACxD,iBAAiB,CAAC,QAAQ,CAC1B,IAAI,KAAK,CAAC,CAEV;MAAA,CAAC,QAAQ,CACX;IAAA,EAAE,eAAe,CAAC,CACnB,CAAA;AACH,CAAC;AAED,MAAM,SAAS,GAAG,GAAG,EAAE;IACrB,MAAM,EAAE,MAAM,EAAE,GAAG,QAAQ,EAAE,CAAA;IAE7B,OAAO,UAAU,CAAC,MAAM,CAAC;QACvB,MAAM,EAAE;YACN,UAAU,EAAE,QAAQ,CAAC,MAAM,CAAC;gBAC1B,GAAG,EAAE,QAAQ;gBACb,OAAO,EAAE,QAAQ;aAClB,CAAC;SACH;QACD,QAAQ,EAAE;YACR,KAAK,EAAE,MAAM,CAAC,wBAAwB;YACtC,QAAQ,EAAE,EAAE,EAAE,uCAAuC;YACrD,UAAU,EAAE,EAAE;SACf;QACD,QAAQ,EAAE;YACR,KAAK,EAAE,MAAM,CAAC,wBAAwB;YACtC,UAAU,EAAE,sBAAsB;YAClC,QAAQ,EAAE,EAAE,EAAE,uCAAuC;YACrD,UAAU,EAAE,EAAE;SACf;QACD,QAAQ,EAAE;YACR,KAAK,EAAE,MAAM,CAAC,wBAAwB;YACtC,UAAU,EAAE,sBAAsB;YAClC,QAAQ,EAAE,MAAM,CAAC,UAAU;YAC3B,UAAU,EAAE,EAAE;SACf;QACD,QAAQ,EAAE;YACR,KAAK,EAAE,MAAM,CAAC,yBAAyB;YACvC,UAAU,EAAE,sBAAsB;YAClC,QAAQ,EAAE,MAAM,CAAC,UAAU;YAC3B,UAAU,EAAE,EAAE;YACd,aAAa,EAAE,WAAW;SAC3B;KACF,CAAC,CAAA;AACJ,CAAC,CAAA","sourcesContent":["import { useTheme } from '../../hooks'\nimport React from 'react'\nimport {\n Platform,\n StyleSheet,\n Text as ReactNativeText,\n TextProps as ReactNativeTextProps,\n} from 'react-native'\nimport { tokens } from '../../vendor/tapestry/tokens'\nimport { platformFontWeightBold } from '../../utils/platform_styles'\n\ninterface TextProps extends ReactNativeTextProps {\n variant?: 'h1' | 'h2' | 'h3' | 'h4'\n}\n\nexport function Heading({ style, variant = 'h1', children, ...props }: TextProps) {\n const styles = useStyles()\n const variantStyleMap = {\n h1: styles.heading1,\n h2: styles.heading2,\n h3: styles.heading3,\n h4: styles.heading4,\n }\n\n return (\n <ReactNativeText\n style={[styles.global, variantStyleMap[variant], style]}\n accessibilityRole=\"header\"\n {...props}\n >\n {children}\n </ReactNativeText>\n )\n}\n\nconst useStyles = () => {\n const { colors } = useTheme()\n\n return StyleSheet.create({\n global: {\n fontFamily: Platform.select({\n ios: 'System',\n android: 'normal',\n }),\n },\n heading1: {\n color: colors.textColorDefaultHeadline,\n fontSize: 25, // Todo: Check with UX on correct token\n lineHeight: 32,\n },\n heading2: {\n color: colors.textColorDefaultHeadline,\n fontWeight: platformFontWeightBold,\n fontSize: 21, // Todo: Check with UX on correct token\n lineHeight: 24,\n },\n heading3: {\n color: colors.textColorDefaultHeadline,\n fontWeight: platformFontWeightBold,\n fontSize: tokens.fontSizeLg,\n lineHeight: 22,\n },\n heading4: {\n color: colors.textColorDefaultSecondary,\n fontWeight: platformFontWeightBold,\n fontSize: tokens.fontSizeSm,\n lineHeight: 20,\n textTransform: 'uppercase',\n },\n })\n}\n"]}
|
|
@@ -1,10 +1,14 @@
|
|
|
1
1
|
import React from 'react';
|
|
2
2
|
import { ImageProps as ReactNativeImageProps, ViewStyle } from 'react-native';
|
|
3
|
-
interface ImageProps extends ReactNativeImageProps {
|
|
3
|
+
export interface ImageProps extends ReactNativeImageProps {
|
|
4
4
|
/**
|
|
5
5
|
* Should the image show the loading indicator by default.
|
|
6
6
|
*/
|
|
7
7
|
defaultLoading?: boolean;
|
|
8
|
+
/**
|
|
9
|
+
* Turn on or off loading spinner.
|
|
10
|
+
*/
|
|
11
|
+
loadingEnabled?: boolean;
|
|
8
12
|
/**
|
|
9
13
|
* Size of the loading spinner.
|
|
10
14
|
*/
|
|
@@ -13,7 +17,10 @@ interface ImageProps extends ReactNativeImageProps {
|
|
|
13
17
|
* Style object for the preload background.
|
|
14
18
|
*/
|
|
15
19
|
loadingBackgroundStyles?: ViewStyle;
|
|
20
|
+
/**
|
|
21
|
+
* Style the outer View of the image.
|
|
22
|
+
*/
|
|
23
|
+
wrapperStyle?: ViewStyle;
|
|
16
24
|
}
|
|
17
|
-
export declare function Image({ source, onLoad, defaultLoading, loaderSize, loadingBackgroundStyles, style, ...
|
|
18
|
-
export {};
|
|
25
|
+
export declare function Image({ source, onLoad, defaultLoading, loadingEnabled, loaderSize, loadingBackgroundStyles, style, wrapperStyle, ...props }: ImageProps): React.JSX.Element;
|
|
19
26
|
//# sourceMappingURL=image.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"image.d.ts","sourceRoot":"","sources":["../../../src/components/display/image.tsx"],"names":[],"mappings":"AACA,OAAO,KAAmB,MAAM,OAAO,CAAA;AACvC,OAAO,EAIL,UAAU,IAAI,qBAAqB,EAGnC,SAAS,EACV,MAAM,cAAc,CAAA;AAIrB,
|
|
1
|
+
{"version":3,"file":"image.d.ts","sourceRoot":"","sources":["../../../src/components/display/image.tsx"],"names":[],"mappings":"AACA,OAAO,KAAmB,MAAM,OAAO,CAAA;AACvC,OAAO,EAIL,UAAU,IAAI,qBAAqB,EAGnC,SAAS,EACV,MAAM,cAAc,CAAA;AAIrB,MAAM,WAAW,UAAW,SAAQ,qBAAqB;IACvD;;OAEG;IACH,cAAc,CAAC,EAAE,OAAO,CAAA;IACxB;;OAEG;IACH,cAAc,CAAC,EAAE,OAAO,CAAA;IACxB;;OAEG;IACH,UAAU,CAAC,EAAE,MAAM,CAAA;IACnB;;OAEG;IACH,uBAAuB,CAAC,EAAE,SAAS,CAAA;IACnC;;OAEG;IACH,YAAY,CAAC,EAAE,SAAS,CAAA;CACzB;AAED,wBAAgB,KAAK,CAAC,EACpB,MAAM,EACN,MAAa,EACb,cAAqB,EACrB,cAAqB,EACrB,UAAe,EACf,uBAAuB,EACvB,KAAU,EACV,YAAiB,EACjB,GAAG,KAAK,EACT,EAAE,UAAU,qBA2BZ"}
|
|
@@ -3,7 +3,7 @@ import React, { useState } from 'react';
|
|
|
3
3
|
import { Image as ReactNativeImage, StyleSheet, View, } from 'react-native';
|
|
4
4
|
import { useTheme } from '../../hooks';
|
|
5
5
|
import { Spinner } from './spinner';
|
|
6
|
-
export function Image({ source, onLoad = noop, defaultLoading = true, loaderSize = 24, loadingBackgroundStyles, style, ...
|
|
6
|
+
export function Image({ source, onLoad = noop, defaultLoading = true, loadingEnabled = true, loaderSize = 24, loadingBackgroundStyles, style = {}, wrapperStyle = {}, ...props }) {
|
|
7
7
|
const [loading, setLoading] = useState(defaultLoading);
|
|
8
8
|
const imageStyles = StyleSheet.flatten(style);
|
|
9
9
|
const { width = '100%', height = '100%', borderRadius = 0 } = imageStyles || {};
|
|
@@ -12,9 +12,9 @@ export function Image({ source, onLoad = noop, defaultLoading = true, loaderSize
|
|
|
12
12
|
setLoading(false);
|
|
13
13
|
onLoad?.(event);
|
|
14
14
|
};
|
|
15
|
-
return (<View>
|
|
16
|
-
<ReactNativeImage style={[styles.image, imageStyles]} onLoad={handleOnLoad} source={source} {...
|
|
17
|
-
{loading && (<View style={[styles.loadingBackground, loadingBackgroundStyles]}>
|
|
15
|
+
return (<View style={wrapperStyle}>
|
|
16
|
+
<ReactNativeImage style={[styles.image, imageStyles]} onLoad={handleOnLoad} source={source} {...props}/>
|
|
17
|
+
{loading && loadingEnabled && (<View style={[styles.loadingBackground, loadingBackgroundStyles]}>
|
|
18
18
|
<Spinner size={loaderSize}/>
|
|
19
19
|
</View>)}
|
|
20
20
|
</View>);
|
|
@@ -32,7 +32,9 @@ const useStyles = (width, height, borderRadius) => {
|
|
|
32
32
|
height,
|
|
33
33
|
},
|
|
34
34
|
image: {
|
|
35
|
-
backgroundColor:
|
|
35
|
+
backgroundColor: colors.fillColorNeutral070,
|
|
36
|
+
width,
|
|
37
|
+
height,
|
|
36
38
|
},
|
|
37
39
|
});
|
|
38
40
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"image.js","sourceRoot":"","sources":["../../../src/components/display/image.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,QAAQ,CAAA;AAC7B,OAAO,KAAK,EAAE,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAA;AACvC,OAAO,EAGL,KAAK,IAAI,gBAAgB,EAEzB,UAAU,EACV,IAAI,GAEL,MAAM,cAAc,CAAA;AACrB,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAA;AACtC,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;
|
|
1
|
+
{"version":3,"file":"image.js","sourceRoot":"","sources":["../../../src/components/display/image.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,QAAQ,CAAA;AAC7B,OAAO,KAAK,EAAE,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAA;AACvC,OAAO,EAGL,KAAK,IAAI,gBAAgB,EAEzB,UAAU,EACV,IAAI,GAEL,MAAM,cAAc,CAAA;AACrB,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAA;AACtC,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AAyBnC,MAAM,UAAU,KAAK,CAAC,EACpB,MAAM,EACN,MAAM,GAAG,IAAI,EACb,cAAc,GAAG,IAAI,EACrB,cAAc,GAAG,IAAI,EACrB,UAAU,GAAG,EAAE,EACf,uBAAuB,EACvB,KAAK,GAAG,EAAE,EACV,YAAY,GAAG,EAAE,EACjB,GAAG,KAAK,EACG;IACX,MAAM,CAAC,OAAO,EAAE,UAAU,CAAC,GAAG,QAAQ,CAAC,cAAc,CAAC,CAAA;IAEtD,MAAM,WAAW,GAAG,UAAU,CAAC,OAAO,CAAC,KAAK,CAAC,CAAA;IAC7C,MAAM,EAAE,KAAK,GAAG,MAAM,EAAE,MAAM,GAAG,MAAM,EAAE,YAAY,GAAG,CAAC,EAAE,GAAG,WAAW,IAAI,EAAE,CAAA;IAC/E,MAAM,MAAM,GAAG,SAAS,CAAC,KAAK,EAAE,MAAM,EAAE,YAAY,CAAC,CAAA;IAErD,MAAM,YAAY,GAAG,CAAC,KAAU,EAAE,EAAE;QAClC,UAAU,CAAC,KAAK,CAAC,CAAA;QACjB,MAAM,EAAE,CAAC,KAAK,CAAC,CAAA;IACjB,CAAC,CAAA;IAED,OAAO,CACL,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,YAAY,CAAC,CACxB;MAAA,CAAC,gBAAgB,CACf,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,EAAE,WAAW,CAAC,CAAC,CACnC,MAAM,CAAC,CAAC,YAAY,CAAC,CACrB,MAAM,CAAC,CAAC,MAAM,CAAC,CACf,IAAI,KAAK,CAAC,EAEZ;MAAA,CAAC,OAAO,IAAI,cAAc,IAAI,CAC5B,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,iBAAiB,EAAE,uBAAuB,CAAC,CAAC,CAC/D;UAAA,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,UAAU,CAAC,EAC5B;QAAA,EAAE,IAAI,CAAC,CACR,CACH;IAAA,EAAE,IAAI,CAAC,CACR,CAAA;AACH,CAAC;AAED,MAAM,SAAS,GAAG,CAChB,KAAqB,EACrB,MAAsB,EACtB,YAA6C,EAC7C,EAAE;IACF,MAAM,EAAE,MAAM,EAAE,GAAG,QAAQ,EAAE,CAAA;IAE7B,OAAO,UAAU,CAAC,MAAM,CAAC;QACvB,iBAAiB,EAAE;YACjB,QAAQ,EAAE,UAAU;YACpB,GAAG,EAAE,CAAC;YACN,IAAI,EAAE,CAAC;YACP,eAAe,EAAE,MAAM,CAAC,mBAAmB;YAC3C,YAAY;YACZ,KAAK;YACL,MAAM;SACP;QACD,KAAK,EAAE;YACL,eAAe,EAAE,MAAM,CAAC,mBAAmB;YAC3C,KAAK;YACL,MAAM;SACP;KACF,CAAC,CAAA;AACJ,CAAC,CAAA","sourcesContent":["import { noop } from 'lodash'\nimport React, { useState } from 'react'\nimport {\n AnimatableNumericValue,\n DimensionValue,\n Image as ReactNativeImage,\n ImageProps as ReactNativeImageProps,\n StyleSheet,\n View,\n ViewStyle,\n} from 'react-native'\nimport { useTheme } from '../../hooks'\nimport { Spinner } from './spinner'\n\nexport interface ImageProps extends ReactNativeImageProps {\n /**\n * Should the image show the loading indicator by default.\n */\n defaultLoading?: boolean\n /**\n * Turn on or off loading spinner.\n */\n loadingEnabled?: boolean\n /**\n * Size of the loading spinner.\n */\n loaderSize?: number\n /**\n * Style object for the preload background.\n */\n loadingBackgroundStyles?: ViewStyle\n /**\n * Style the outer View of the image.\n */\n wrapperStyle?: ViewStyle\n}\n\nexport function Image({\n source,\n onLoad = noop,\n defaultLoading = true,\n loadingEnabled = true,\n loaderSize = 24,\n loadingBackgroundStyles,\n style = {},\n wrapperStyle = {},\n ...props\n}: ImageProps) {\n const [loading, setLoading] = useState(defaultLoading)\n\n const imageStyles = StyleSheet.flatten(style)\n const { width = '100%', height = '100%', borderRadius = 0 } = imageStyles || {}\n const styles = useStyles(width, height, borderRadius)\n\n const handleOnLoad = (event: any) => {\n setLoading(false)\n onLoad?.(event)\n }\n\n return (\n <View style={wrapperStyle}>\n <ReactNativeImage\n style={[styles.image, imageStyles]}\n onLoad={handleOnLoad}\n source={source}\n {...props}\n />\n {loading && loadingEnabled && (\n <View style={[styles.loadingBackground, loadingBackgroundStyles]}>\n <Spinner size={loaderSize} />\n </View>\n )}\n </View>\n )\n}\n\nconst useStyles = (\n width: DimensionValue,\n height: DimensionValue,\n borderRadius: AnimatableNumericValue | string\n) => {\n const { colors } = useTheme()\n\n return StyleSheet.create({\n loadingBackground: {\n position: 'absolute',\n top: 0,\n left: 0,\n backgroundColor: colors.fillColorNeutral070,\n borderRadius,\n width,\n height,\n },\n image: {\n backgroundColor: colors.fillColorNeutral070,\n width,\n height,\n },\n })\n}\n"]}
|
|
@@ -1,4 +1,7 @@
|
|
|
1
|
+
export { Avatar } from './avatar';
|
|
2
|
+
export { AvatarGroup } from './avatar_group';
|
|
3
|
+
export { Heading } from './heading';
|
|
4
|
+
export { Image, ImageProps } from './image';
|
|
1
5
|
export { Spinner } from './spinner';
|
|
2
|
-
export { Image } from './image';
|
|
3
6
|
export { Text } from './text';
|
|
4
7
|
//# sourceMappingURL=index.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/display/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,KAAK,EAAE,MAAM,SAAS,CAAA;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/components/display/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAA;AACjC,OAAO,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAA;AAC5C,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,KAAK,EAAE,UAAU,EAAE,MAAM,SAAS,CAAA;AAC3C,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,IAAI,EAAE,MAAM,QAAQ,CAAA"}
|
|
@@ -1,4 +1,7 @@
|
|
|
1
|
-
export {
|
|
1
|
+
export { Avatar } from './avatar';
|
|
2
|
+
export { AvatarGroup } from './avatar_group';
|
|
3
|
+
export { Heading } from './heading';
|
|
2
4
|
export { Image } from './image';
|
|
5
|
+
export { Spinner } from './spinner';
|
|
3
6
|
export { Text } from './text';
|
|
4
7
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/components/display/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,KAAK,
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/components/display/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,UAAU,CAAA;AACjC,OAAO,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAA;AAC5C,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,KAAK,EAAc,MAAM,SAAS,CAAA;AAC3C,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAA;AACnC,OAAO,EAAE,IAAI,EAAE,MAAM,QAAQ,CAAA","sourcesContent":["export { Avatar } from './avatar'\nexport { AvatarGroup } from './avatar_group'\nexport { Heading } from './heading'\nexport { Image, ImageProps } from './image'\nexport { Spinner } from './spinner'\nexport { Text } from './text'\n"]}
|
|
@@ -3,6 +3,6 @@ import { TextProps as ReactNativeTextProps } from 'react-native';
|
|
|
3
3
|
interface TextProps extends ReactNativeTextProps {
|
|
4
4
|
variant?: 'plain' | 'secondary' | 'tertiary' | 'footnote';
|
|
5
5
|
}
|
|
6
|
-
export declare function Text({ style, variant, children, ...
|
|
6
|
+
export declare function Text({ style, variant, children, ...props }: TextProps): React.JSX.Element;
|
|
7
7
|
export {};
|
|
8
8
|
//# sourceMappingURL=text.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"text.d.ts","sourceRoot":"","sources":["../../../src/components/display/text.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,EAIL,SAAS,IAAI,oBAAoB,EAClC,MAAM,cAAc,CAAA;
|
|
1
|
+
{"version":3,"file":"text.d.ts","sourceRoot":"","sources":["../../../src/components/display/text.tsx"],"names":[],"mappings":"AACA,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,EAIL,SAAS,IAAI,oBAAoB,EAClC,MAAM,cAAc,CAAA;AAGrB,UAAU,SAAU,SAAQ,oBAAoB;IAC9C,OAAO,CAAC,EAAE,OAAO,GAAG,WAAW,GAAG,UAAU,GAAG,UAAU,CAAA;CAC1D;AAED,wBAAgB,IAAI,CAAC,EAAE,KAAK,EAAE,OAAiB,EAAE,QAAQ,EAAE,GAAG,KAAK,EAAE,EAAE,SAAS,qBAc/E"}
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import { useTheme } from '../../hooks';
|
|
2
2
|
import React from 'react';
|
|
3
3
|
import { Platform, StyleSheet, Text as ReactNativeText, } from 'react-native';
|
|
4
|
-
|
|
4
|
+
import { tokens } from '../../vendor/tapestry/tokens';
|
|
5
|
+
export function Text({ style, variant = 'plain', children, ...props }) {
|
|
5
6
|
const styles = useStyles();
|
|
6
7
|
const variantStyleMap = {
|
|
7
8
|
plain: styles.plain,
|
|
@@ -9,7 +10,7 @@ export function Text({ style, variant = 'plain', children, ...rest }) {
|
|
|
9
10
|
tertiary: styles.tertiary,
|
|
10
11
|
footnote: styles.footnote,
|
|
11
12
|
};
|
|
12
|
-
return (<ReactNativeText style={[styles.global, variantStyleMap[variant], style]} {...
|
|
13
|
+
return (<ReactNativeText style={[styles.global, variantStyleMap[variant], style]} {...props}>
|
|
13
14
|
{children}
|
|
14
15
|
</ReactNativeText>);
|
|
15
16
|
}
|
|
@@ -24,22 +25,22 @@ const useStyles = () => {
|
|
|
24
25
|
},
|
|
25
26
|
plain: {
|
|
26
27
|
color: colors.textColorDefaultPrimary,
|
|
27
|
-
fontSize:
|
|
28
|
+
fontSize: tokens.fontSizeMd,
|
|
28
29
|
lineHeight: 24,
|
|
29
30
|
},
|
|
30
31
|
secondary: {
|
|
31
32
|
color: colors.textColorDefaultPrimary,
|
|
32
|
-
fontSize: 15,
|
|
33
|
+
fontSize: 15, // TODO: Check with UX on correct token
|
|
33
34
|
lineHeight: 22,
|
|
34
35
|
},
|
|
35
36
|
tertiary: {
|
|
36
37
|
color: colors.textColorDefaultPrimary,
|
|
37
|
-
fontSize:
|
|
38
|
+
fontSize: tokens.fontSizeSm,
|
|
38
39
|
lineHeight: 20,
|
|
39
40
|
},
|
|
40
41
|
footnote: {
|
|
41
42
|
color: colors.textColorDefaultSecondary,
|
|
42
|
-
fontSize: 13,
|
|
43
|
+
fontSize: 13, // TODO: Check with UX on correct token
|
|
43
44
|
lineHeight: 16,
|
|
44
45
|
},
|
|
45
46
|
});
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"text.js","sourceRoot":"","sources":["../../../src/components/display/text.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAA;AACtC,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,EACL,QAAQ,EACR,UAAU,EACV,IAAI,IAAI,eAAe,GAExB,MAAM,cAAc,CAAA;
|
|
1
|
+
{"version":3,"file":"text.js","sourceRoot":"","sources":["../../../src/components/display/text.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAA;AACtC,OAAO,KAAK,MAAM,OAAO,CAAA;AACzB,OAAO,EACL,QAAQ,EACR,UAAU,EACV,IAAI,IAAI,eAAe,GAExB,MAAM,cAAc,CAAA;AACrB,OAAO,EAAE,MAAM,EAAE,MAAM,8BAA8B,CAAA;AAMrD,MAAM,UAAU,IAAI,CAAC,EAAE,KAAK,EAAE,OAAO,GAAG,OAAO,EAAE,QAAQ,EAAE,GAAG,KAAK,EAAa;IAC9E,MAAM,MAAM,GAAG,SAAS,EAAE,CAAA;IAC1B,MAAM,eAAe,GAAG;QACtB,KAAK,EAAE,MAAM,CAAC,KAAK;QACnB,SAAS,EAAE,MAAM,CAAC,SAAS;QAC3B,QAAQ,EAAE,MAAM,CAAC,QAAQ;QACzB,QAAQ,EAAE,MAAM,CAAC,QAAQ;KAC1B,CAAA;IAED,OAAO,CACL,CAAC,eAAe,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,MAAM,EAAE,eAAe,CAAC,OAAO,CAAC,EAAE,KAAK,CAAC,CAAC,CAAC,IAAI,KAAK,CAAC,CAClF;MAAA,CAAC,QAAQ,CACX;IAAA,EAAE,eAAe,CAAC,CACnB,CAAA;AACH,CAAC;AAED,MAAM,SAAS,GAAG,GAAG,EAAE;IACrB,MAAM,EAAE,MAAM,EAAE,GAAG,QAAQ,EAAE,CAAA;IAC7B,OAAO,UAAU,CAAC,MAAM,CAAC;QACvB,MAAM,EAAE;YACN,UAAU,EAAE,QAAQ,CAAC,MAAM,CAAC;gBAC1B,GAAG,EAAE,QAAQ;gBACb,OAAO,EAAE,QAAQ;aAClB,CAAC;SACH;QACD,KAAK,EAAE;YACL,KAAK,EAAE,MAAM,CAAC,uBAAuB;YACrC,QAAQ,EAAE,MAAM,CAAC,UAAU;YAC3B,UAAU,EAAE,EAAE;SACf;QACD,SAAS,EAAE;YACT,KAAK,EAAE,MAAM,CAAC,uBAAuB;YACrC,QAAQ,EAAE,EAAE,EAAE,uCAAuC;YACrD,UAAU,EAAE,EAAE;SACf;QACD,QAAQ,EAAE;YACR,KAAK,EAAE,MAAM,CAAC,uBAAuB;YACrC,QAAQ,EAAE,MAAM,CAAC,UAAU;YAC3B,UAAU,EAAE,EAAE;SACf;QACD,QAAQ,EAAE;YACR,KAAK,EAAE,MAAM,CAAC,yBAAyB;YACvC,QAAQ,EAAE,EAAE,EAAE,uCAAuC;YACrD,UAAU,EAAE,EAAE;SACf;KACF,CAAC,CAAA;AACJ,CAAC,CAAA","sourcesContent":["import { useTheme } from '../../hooks'\nimport React from 'react'\nimport {\n Platform,\n StyleSheet,\n Text as ReactNativeText,\n TextProps as ReactNativeTextProps,\n} from 'react-native'\nimport { tokens } from '../../vendor/tapestry/tokens'\n\ninterface TextProps extends ReactNativeTextProps {\n variant?: 'plain' | 'secondary' | 'tertiary' | 'footnote'\n}\n\nexport function Text({ style, variant = 'plain', children, ...props }: TextProps) {\n const styles = useStyles()\n const variantStyleMap = {\n plain: styles.plain,\n secondary: styles.secondary,\n tertiary: styles.tertiary,\n footnote: styles.footnote,\n }\n\n return (\n <ReactNativeText style={[styles.global, variantStyleMap[variant], style]} {...props}>\n {children}\n </ReactNativeText>\n )\n}\n\nconst useStyles = () => {\n const { colors } = useTheme()\n return StyleSheet.create({\n global: {\n fontFamily: Platform.select({\n ios: 'System',\n android: 'normal',\n }),\n },\n plain: {\n color: colors.textColorDefaultPrimary,\n fontSize: tokens.fontSizeMd,\n lineHeight: 24,\n },\n secondary: {\n color: colors.textColorDefaultPrimary,\n fontSize: 15, // TODO: Check with UX on correct token\n lineHeight: 22,\n },\n tertiary: {\n color: colors.textColorDefaultPrimary,\n fontSize: tokens.fontSizeSm,\n lineHeight: 20,\n },\n footnote: {\n color: colors.textColorDefaultSecondary,\n fontSize: 13, // TODO: Check with UX on correct token\n lineHeight: 16,\n },\n })\n}\n"]}
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
import React from 'react';
|
|
2
|
+
import { ViewProps } from 'react-native';
|
|
3
|
+
import { ImageProps } from '../display/image';
|
|
4
|
+
type AvatarComponents = {
|
|
5
|
+
Root: React.FC<AvatarRootProps>;
|
|
6
|
+
Image: React.FC<AvatarImageProps>;
|
|
7
|
+
Presence: React.FC<AvatarPresenceProps>;
|
|
8
|
+
Group: React.FC<AvatarGroupProps>;
|
|
9
|
+
GroupLoader: React.FC<Record<string, never>>;
|
|
10
|
+
Mask: React.FC<AvatarMaskProps>;
|
|
11
|
+
};
|
|
12
|
+
declare const _default: AvatarComponents;
|
|
13
|
+
export default _default;
|
|
14
|
+
export type { AvatarImageProps, AvatarPresenceProps, AvatarGroupProps, AvatarMaskProps, AvatarRootProps, };
|
|
15
|
+
declare const AVATAR_SIZES: {
|
|
16
|
+
readonly md: "md";
|
|
17
|
+
readonly lg: "lg";
|
|
18
|
+
};
|
|
19
|
+
declare const AVATAR_PRESENCE_TYPES: {
|
|
20
|
+
readonly online: "online";
|
|
21
|
+
readonly offline: "offline";
|
|
22
|
+
};
|
|
23
|
+
type AvatarSize = (typeof AVATAR_SIZES)[keyof typeof AVATAR_SIZES];
|
|
24
|
+
type AvatarPresenceType = (typeof AVATAR_PRESENCE_TYPES)[keyof typeof AVATAR_PRESENCE_TYPES];
|
|
25
|
+
interface AvatarRootProps {
|
|
26
|
+
children: React.ReactNode;
|
|
27
|
+
size?: AvatarSize;
|
|
28
|
+
}
|
|
29
|
+
type AvatarMaskProps = ViewProps;
|
|
30
|
+
interface AvatarImageProps extends Omit<ImageProps, 'source'> {
|
|
31
|
+
sourceUri: string;
|
|
32
|
+
}
|
|
33
|
+
interface AvatarGroupProps {
|
|
34
|
+
sourceUris: string[];
|
|
35
|
+
}
|
|
36
|
+
interface AvatarPresenceProps extends ViewProps {
|
|
37
|
+
presence: AvatarPresenceType;
|
|
38
|
+
}
|
|
39
|
+
//# sourceMappingURL=avatar_primitive.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"avatar_primitive.d.ts","sourceRoot":"","sources":["../../../src/components/primitive/avatar_primitive.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAyD,MAAM,OAAO,CAAA;AAC7E,OAAO,EAAoB,SAAS,EAAE,MAAM,cAAc,CAAA;AAE1D,OAAO,EAAS,UAAU,EAAE,MAAM,kBAAkB,CAAA;AAgBpD,KAAK,gBAAgB,GAAG;IACtB,IAAI,EAAE,KAAK,CAAC,EAAE,CAAC,eAAe,CAAC,CAAA;IAC/B,KAAK,EAAE,KAAK,CAAC,EAAE,CAAC,gBAAgB,CAAC,CAAA;IACjC,QAAQ,EAAE,KAAK,CAAC,EAAE,CAAC,mBAAmB,CAAC,CAAA;IACvC,KAAK,EAAE,KAAK,CAAC,EAAE,CAAC,gBAAgB,CAAC,CAAA;IACjC,WAAW,EAAE,KAAK,CAAC,EAAE,CAAC,MAAM,CAAC,MAAM,EAAE,KAAK,CAAC,CAAC,CAAA;IAC5C,IAAI,EAAE,KAAK,CAAC,EAAE,CAAC,eAAe,CAAC,CAAA;CAChC,CAAA;wBAEwB,gBAAgB;AAAzC,wBAAyC;AACzC,YAAY,EACV,gBAAgB,EAChB,mBAAmB,EACnB,gBAAgB,EAChB,eAAe,EACf,eAAe,GAChB,CAAA;AAMD,QAAA,MAAM,YAAY;;;CAGR,CAAA;AAEV,QAAA,MAAM,qBAAqB;;;CAGjB,CAAA;AAGV,KAAK,UAAU,GAAG,CAAC,OAAO,YAAY,CAAC,CAAC,MAAM,OAAO,YAAY,CAAC,CAAA;AAClE,KAAK,kBAAkB,GAAG,CAAC,OAAO,qBAAqB,CAAC,CAAC,MAAM,OAAO,qBAAqB,CAAC,CAAA;AAoC5F,UAAU,eAAe;IACvB,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAA;IACzB,IAAI,CAAC,EAAE,UAAU,CAAA;CAClB;AAmBD,KAAK,eAAe,GAAG,SAAS,CAAA;AAkBhC,UAAU,gBAAiB,SAAQ,IAAI,CAAC,UAAU,EAAE,QAAQ,CAAC;IAC3D,SAAS,EAAE,MAAM,CAAA;CAClB;AA+BD,UAAU,gBAAgB;IACxB,UAAU,EAAE,MAAM,EAAE,CAAA;CACrB;AAsID,UAAU,mBAAoB,SAAQ,SAAS;IAC7C,QAAQ,EAAE,kBAAkB,CAAA;CAC7B"}
|
|
@@ -0,0 +1,204 @@
|
|
|
1
|
+
import React, { createContext, useContext, useEffect, useState } from 'react';
|
|
2
|
+
import { StyleSheet, View } from 'react-native';
|
|
3
|
+
import { useTheme } from '../../hooks';
|
|
4
|
+
import { Image } from '../display/image';
|
|
5
|
+
import { Spinner } from '../display/spinner';
|
|
6
|
+
// =================================
|
|
7
|
+
// ====== Exports ==================
|
|
8
|
+
// =================================
|
|
9
|
+
const Avatar = {
|
|
10
|
+
Root: AvatarRoot,
|
|
11
|
+
Image: AvatarImage,
|
|
12
|
+
Presence: AvatarPresence,
|
|
13
|
+
Group: AvatarGroup,
|
|
14
|
+
GroupLoader: AvatarGroupLoader,
|
|
15
|
+
Mask: AvatarMask,
|
|
16
|
+
};
|
|
17
|
+
export default Avatar;
|
|
18
|
+
// =================================
|
|
19
|
+
// ====== Constants & Types ========
|
|
20
|
+
// =================================
|
|
21
|
+
const AVATAR_SIZES = {
|
|
22
|
+
md: 'md',
|
|
23
|
+
lg: 'lg',
|
|
24
|
+
};
|
|
25
|
+
const AVATAR_PRESENCE_TYPES = {
|
|
26
|
+
online: 'online',
|
|
27
|
+
offline: 'offline',
|
|
28
|
+
};
|
|
29
|
+
const AVATAR_PX = {
|
|
30
|
+
[AVATAR_SIZES.md]: 32,
|
|
31
|
+
[AVATAR_SIZES.lg]: 40,
|
|
32
|
+
};
|
|
33
|
+
const AVATAR_PRESENCE_PX = {
|
|
34
|
+
[AVATAR_SIZES.md]: 12,
|
|
35
|
+
[AVATAR_SIZES.lg]: 14,
|
|
36
|
+
};
|
|
37
|
+
const AvatarContext = createContext(null);
|
|
38
|
+
function useAvatarContext() {
|
|
39
|
+
const context = useContext(AvatarContext);
|
|
40
|
+
if (!context) {
|
|
41
|
+
throw new Error('Avatar components must be used within Avatar.Root');
|
|
42
|
+
}
|
|
43
|
+
return context;
|
|
44
|
+
}
|
|
45
|
+
function AvatarRoot({ children, size = 'md' }) {
|
|
46
|
+
const [allImagesLoaded, setAllImagesLoaded] = useState(false);
|
|
47
|
+
const styles = useStyles(size);
|
|
48
|
+
return (<AvatarContext.Provider value={{ size, allImagesLoaded, setAllImagesLoaded }}>
|
|
49
|
+
<View style={styles.rootContainer}>{children}</View>
|
|
50
|
+
</AvatarContext.Provider>);
|
|
51
|
+
}
|
|
52
|
+
AvatarRoot.displayName = 'Avatar.Root';
|
|
53
|
+
function AvatarMask({ children, ...props }) {
|
|
54
|
+
const styles = useStyles();
|
|
55
|
+
return (<View style={styles.mask} {...props}>
|
|
56
|
+
{children}
|
|
57
|
+
</View>);
|
|
58
|
+
}
|
|
59
|
+
AvatarMask.displayName = 'Avatar.Mask';
|
|
60
|
+
function AvatarImage({ sourceUri, ...props }) {
|
|
61
|
+
const { size } = useAvatarContext();
|
|
62
|
+
return <Image source={{ uri: sourceUri }} loaderSize={AVATAR_PX[size]} {...props}/>;
|
|
63
|
+
}
|
|
64
|
+
AvatarImage.displayName = 'Avatar.Image';
|
|
65
|
+
function AvatarGroupImage({ sourceUri, style, onLoad }) {
|
|
66
|
+
return (<Image source={{ uri: sourceUri }} loadingEnabled={false} wrapperStyle={style} onLoad={onLoad}/>);
|
|
67
|
+
}
|
|
68
|
+
function AvatarGroup({ sourceUris }) {
|
|
69
|
+
const styles = useStyles();
|
|
70
|
+
const { setAllImagesLoaded } = useAvatarContext();
|
|
71
|
+
const [loadingStatus, setLoadingStatus] = useState({
|
|
72
|
+
0: false,
|
|
73
|
+
1: false,
|
|
74
|
+
2: false,
|
|
75
|
+
3: false,
|
|
76
|
+
});
|
|
77
|
+
const displayUris = sourceUris.slice(0, 4);
|
|
78
|
+
const hasDisplayUris = displayUris.length > 0;
|
|
79
|
+
const handleImageLoaded = index => {
|
|
80
|
+
setLoadingStatus(prev => ({
|
|
81
|
+
...prev,
|
|
82
|
+
[index]: true,
|
|
83
|
+
}));
|
|
84
|
+
};
|
|
85
|
+
useEffect(() => {
|
|
86
|
+
const allImagesLoaded = hasDisplayUris && displayUris.every((_, index) => loadingStatus[index] === true);
|
|
87
|
+
setAllImagesLoaded(allImagesLoaded);
|
|
88
|
+
}, [displayUris, hasDisplayUris, loadingStatus, setAllImagesLoaded]);
|
|
89
|
+
if (!hasDisplayUris) {
|
|
90
|
+
return null;
|
|
91
|
+
}
|
|
92
|
+
if (displayUris.length === 1) {
|
|
93
|
+
return <AvatarGroupImage sourceUri={displayUris[0]} onLoad={() => handleImageLoaded(0)}/>;
|
|
94
|
+
}
|
|
95
|
+
if (displayUris.length === 2) {
|
|
96
|
+
return (<View style={styles.groupRow}>
|
|
97
|
+
<AvatarGroupImage sourceUri={displayUris[0]} style={styles.halfWidthFullHeight} onLoad={() => handleImageLoaded(0)}/>
|
|
98
|
+
<AvatarGroupImage sourceUri={displayUris[1]} style={styles.halfWidthFullHeight} onLoad={() => handleImageLoaded(1)}/>
|
|
99
|
+
</View>);
|
|
100
|
+
}
|
|
101
|
+
if (displayUris.length === 3) {
|
|
102
|
+
return (<View style={styles.groupColumn}>
|
|
103
|
+
<View style={styles.groupRow}>
|
|
104
|
+
<AvatarGroupImage sourceUri={displayUris[0]} style={styles.halfWidthFullHeight} onLoad={() => handleImageLoaded(0)}/>
|
|
105
|
+
<View style={styles.groupColumn}>
|
|
106
|
+
<AvatarGroupImage sourceUri={displayUris[1]} style={styles.fullWidthHalfHeight} onLoad={() => handleImageLoaded(1)}/>
|
|
107
|
+
<AvatarGroupImage sourceUri={displayUris[2]} style={styles.fullWidthHalfHeight} onLoad={() => handleImageLoaded(2)}/>
|
|
108
|
+
</View>
|
|
109
|
+
</View>
|
|
110
|
+
</View>);
|
|
111
|
+
}
|
|
112
|
+
return (<View style={styles.groupColumn}>
|
|
113
|
+
<View style={styles.groupRow}>
|
|
114
|
+
<AvatarGroupImage sourceUri={displayUris[0]} style={styles.halfWidthFullHeight} onLoad={() => handleImageLoaded(0)}/>
|
|
115
|
+
<AvatarGroupImage sourceUri={displayUris[1]} style={styles.halfWidthFullHeight} onLoad={() => handleImageLoaded(1)}/>
|
|
116
|
+
</View>
|
|
117
|
+
<View style={styles.groupRow}>
|
|
118
|
+
<AvatarGroupImage sourceUri={displayUris[2]} style={styles.halfWidthFullHeight} onLoad={() => handleImageLoaded(2)}/>
|
|
119
|
+
<AvatarGroupImage sourceUri={displayUris[3]} style={styles.halfWidthFullHeight} onLoad={() => handleImageLoaded(3)}/>
|
|
120
|
+
</View>
|
|
121
|
+
</View>);
|
|
122
|
+
}
|
|
123
|
+
AvatarGroup.displayName = 'Avatar.Group';
|
|
124
|
+
// =================================
|
|
125
|
+
// ====== AvatarGroupLoader =========
|
|
126
|
+
// =================================
|
|
127
|
+
function AvatarGroupLoader() {
|
|
128
|
+
const { size, allImagesLoaded } = useAvatarContext();
|
|
129
|
+
const styles = useStyles(size);
|
|
130
|
+
if (allImagesLoaded)
|
|
131
|
+
return null;
|
|
132
|
+
return (<View style={styles.groupLoader}>
|
|
133
|
+
<Spinner size={AVATAR_PX[size]}/>
|
|
134
|
+
</View>);
|
|
135
|
+
}
|
|
136
|
+
AvatarGroupLoader.displayName = 'Avatar.GroupLoader';
|
|
137
|
+
function AvatarPresence({ presence, ...props }) {
|
|
138
|
+
const { size } = useAvatarContext();
|
|
139
|
+
const styles = useStyles(size, presence);
|
|
140
|
+
return <View style={styles.presence} {...props}/>;
|
|
141
|
+
}
|
|
142
|
+
AvatarPresence.displayName = 'Avatar.Presence';
|
|
143
|
+
// =================================
|
|
144
|
+
// ====== Styles ===================
|
|
145
|
+
// =================================
|
|
146
|
+
const useStyles = (size = 'md', presence = 'offline') => {
|
|
147
|
+
const { colors } = useTheme();
|
|
148
|
+
const PRESENCE_COLOR = {
|
|
149
|
+
online: colors.fillColorInteractionOnlineDefault,
|
|
150
|
+
offline: colors.iconColorDefaultDisabled,
|
|
151
|
+
};
|
|
152
|
+
const presenceDiameter = AVATAR_PRESENCE_PX[size];
|
|
153
|
+
const avatarDiameter = AVATAR_PX[size];
|
|
154
|
+
const groupGap = 1;
|
|
155
|
+
return StyleSheet.create({
|
|
156
|
+
rootContainer: {
|
|
157
|
+
height: avatarDiameter,
|
|
158
|
+
width: avatarDiameter,
|
|
159
|
+
},
|
|
160
|
+
mask: {
|
|
161
|
+
borderRadius: avatarDiameter,
|
|
162
|
+
overflow: 'hidden',
|
|
163
|
+
width: '100%',
|
|
164
|
+
height: '100%',
|
|
165
|
+
},
|
|
166
|
+
presence: {
|
|
167
|
+
height: presenceDiameter,
|
|
168
|
+
width: presenceDiameter,
|
|
169
|
+
backgroundColor: PRESENCE_COLOR[presence],
|
|
170
|
+
borderColor: colors.fillColorNeutral100Inverted,
|
|
171
|
+
borderWidth: 2,
|
|
172
|
+
borderRadius: presenceDiameter,
|
|
173
|
+
position: 'absolute',
|
|
174
|
+
bottom: -1,
|
|
175
|
+
right: -1,
|
|
176
|
+
},
|
|
177
|
+
groupLoader: {
|
|
178
|
+
position: 'absolute',
|
|
179
|
+
top: 0,
|
|
180
|
+
left: 0,
|
|
181
|
+
borderRadius: avatarDiameter,
|
|
182
|
+
width: avatarDiameter,
|
|
183
|
+
height: avatarDiameter,
|
|
184
|
+
},
|
|
185
|
+
groupColumn: {
|
|
186
|
+
flex: 1,
|
|
187
|
+
gap: groupGap,
|
|
188
|
+
},
|
|
189
|
+
groupRow: {
|
|
190
|
+
flexDirection: 'row',
|
|
191
|
+
flex: 1,
|
|
192
|
+
gap: groupGap,
|
|
193
|
+
},
|
|
194
|
+
halfWidthFullHeight: {
|
|
195
|
+
width: '50%',
|
|
196
|
+
height: '100%',
|
|
197
|
+
},
|
|
198
|
+
fullWidthHalfHeight: {
|
|
199
|
+
width: '100%',
|
|
200
|
+
height: '50%',
|
|
201
|
+
},
|
|
202
|
+
});
|
|
203
|
+
};
|
|
204
|
+
//# sourceMappingURL=avatar_primitive.js.map
|