@cairntale/chimeling-react 1.0.0-alpha.5 → 1.0.0-alpha.7
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 +20 -0
- package/dist/components/index.d.ts +2 -2
- package/dist/components/playground/panel.js +142 -10
- package/dist/components/playground/panel.js.map +1 -1
- package/dist/components/playground/playground.d.ts +3 -1
- package/dist/components/playground/playground.js +45 -18
- package/dist/components/playground/playground.js.map +1 -1
- package/dist/components/playground/store.js +49 -8
- package/dist/components/playground/store.js.map +1 -1
- package/dist/components/popover.d.ts +9 -2
- package/dist/components/popover.js +117 -15
- package/dist/components/popover.js.map +1 -1
- package/dist/components/provider.d.ts +8 -1
- package/dist/components/provider.js +46 -11
- package/dist/components/provider.js.map +1 -1
- package/dist/components/root.js +8 -4
- package/dist/components/root.js.map +1 -1
- package/dist/components/trigger.d.ts +7 -2
- package/dist/components/trigger.js +67 -5
- package/dist/components/trigger.js.map +1 -1
- package/dist/index.d.ts +2 -2
- package/dist/lib/use-client-committed.js +14 -0
- package/dist/lib/use-client-committed.js.map +1 -0
- package/dist/lib/widget-context.d.ts +3 -1
- package/dist/lib/widget-context.js.map +1 -1
- package/dist/theme/color-system.d.ts +1 -0
- package/dist/theme/color-system.js +96 -0
- package/dist/theme/color-system.js.map +1 -0
- package/dist/theme/context.d.ts +2 -0
- package/dist/theme/context.js +15 -0
- package/dist/theme/context.js.map +1 -0
- package/dist/theme/index.d.ts +4 -0
- package/dist/theme/index.js +4 -0
- package/dist/theme/tokens.d.ts +6 -0
- package/dist/theme/tokens.js +69 -0
- package/dist/theme/tokens.js.map +1 -0
- package/package.json +2 -1
|
@@ -3,34 +3,136 @@ import { useWidgetContext } from "../lib/widget-context.js";
|
|
|
3
3
|
import { formatActivityDuration } from "../lib/format-activity-duration.js";
|
|
4
4
|
import { iconImageUrl } from "../lib/icon-url.js";
|
|
5
5
|
import Logo from "./logo.js";
|
|
6
|
+
import { ClassNames } from "@emotion/react";
|
|
6
7
|
import { jsx, jsxs } from "react/jsx-runtime";
|
|
7
8
|
import { Popover } from "@base-ui/react/popover";
|
|
8
9
|
//#region src/components/popover.tsx
|
|
9
|
-
|
|
10
|
+
const DEFAULT_POPOVER = {
|
|
11
|
+
ring: true,
|
|
12
|
+
shadow: "elevated",
|
|
13
|
+
minWidth: 320,
|
|
14
|
+
gerundCapitalize: true,
|
|
15
|
+
gerundEllipsis: true
|
|
16
|
+
};
|
|
17
|
+
const iconSize = "calc(22px * var(--chl-font-size-scaling, 1))";
|
|
18
|
+
function ChimelingPopover({ className, style, ring = DEFAULT_POPOVER.ring, shadow = DEFAULT_POPOVER.shadow, minWidth = DEFAULT_POPOVER.minWidth, gerundCapitalize = DEFAULT_POPOVER.gerundCapitalize, gerundEllipsis = DEFAULT_POPOVER.gerundEllipsis }) {
|
|
10
19
|
const { showable, now, poweredBy, placement, baseUrl } = useWidgetContext();
|
|
11
20
|
if (!showable) return null;
|
|
12
21
|
const { gerund, appName, iconHash, startedAt } = showable.activity;
|
|
13
|
-
return /* @__PURE__ */ jsx(Popover.Portal, { children: /* @__PURE__ */ jsx(Popover.Positioner, {
|
|
22
|
+
return /* @__PURE__ */ jsx(ClassNames, { children: ({ css, cx }) => /* @__PURE__ */ jsx(Popover.Portal, { children: /* @__PURE__ */ jsx(Popover.Positioner, {
|
|
14
23
|
side: placement.side,
|
|
15
24
|
align: placement.align,
|
|
16
25
|
sideOffset: placement.sideOffset,
|
|
17
26
|
children: /* @__PURE__ */ jsxs(Popover.Popup, {
|
|
18
|
-
className,
|
|
27
|
+
className: cx("chl-popover", css({
|
|
28
|
+
boxSizing: "border-box",
|
|
29
|
+
display: "flex",
|
|
30
|
+
flexDirection: "column",
|
|
31
|
+
minWidth,
|
|
32
|
+
overflow: "clip",
|
|
33
|
+
padding: 0,
|
|
34
|
+
margin: 0,
|
|
35
|
+
outline: "none",
|
|
36
|
+
color: "var(--chl-color-text-primary)",
|
|
37
|
+
backgroundColor: "var(--chl-color-background-primary)",
|
|
38
|
+
borderRadius: "var(--chl-border-radius-lg)",
|
|
39
|
+
border: "none",
|
|
40
|
+
boxShadow: [
|
|
41
|
+
...shadow === "subtle" ? ["var(--chl-shadow-subtle)"] : [],
|
|
42
|
+
...shadow === "elevated" ? ["var(--chl-shadow-elevated)"] : [],
|
|
43
|
+
...ring ? ["var(--chl-ring)"] : []
|
|
44
|
+
].join(", ") || "none"
|
|
45
|
+
}), className),
|
|
19
46
|
style,
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
47
|
+
"data-ring": ring ? "true" : "false",
|
|
48
|
+
"data-shadow": shadow,
|
|
49
|
+
"data-gerund-capitalize": gerundCapitalize ? "true" : "false",
|
|
50
|
+
"data-gerund-ellipsis": gerundEllipsis ? "true" : "false",
|
|
51
|
+
children: [/* @__PURE__ */ jsxs("div", {
|
|
52
|
+
className: css({
|
|
53
|
+
display: "flex",
|
|
54
|
+
flexDirection: "column",
|
|
55
|
+
gap: "var(--chl-spacing-2xs)",
|
|
56
|
+
padding: "var(--chl-spacing-sm)"
|
|
57
|
+
}),
|
|
58
|
+
children: [
|
|
59
|
+
/* @__PURE__ */ jsx(Popover.Description, {
|
|
60
|
+
className: css({
|
|
61
|
+
margin: 0,
|
|
62
|
+
fontSize: "var(--chl-font-size-sm)",
|
|
63
|
+
fontWeight: 400,
|
|
64
|
+
color: "var(--chl-color-text-tertiary)",
|
|
65
|
+
"[data-gerund-capitalize=\"true\"] &::first-letter": { textTransform: "uppercase" },
|
|
66
|
+
"[data-gerund-ellipsis=\"true\"] &::after": { content: "\"...\"" }
|
|
67
|
+
}),
|
|
68
|
+
children: gerund
|
|
69
|
+
}),
|
|
70
|
+
/* @__PURE__ */ jsxs("div", {
|
|
71
|
+
className: css({
|
|
72
|
+
display: "flex",
|
|
73
|
+
alignItems: "center",
|
|
74
|
+
gap: "var(--chl-spacing-2xs)",
|
|
75
|
+
minWidth: 0
|
|
76
|
+
}),
|
|
77
|
+
children: [iconHash ? /* @__PURE__ */ jsx("img", {
|
|
78
|
+
src: iconImageUrl(baseUrl, iconHash),
|
|
79
|
+
alt: "",
|
|
80
|
+
width: 24,
|
|
81
|
+
height: 24,
|
|
82
|
+
className: css({
|
|
83
|
+
display: "block",
|
|
84
|
+
flex: "0 0 auto",
|
|
85
|
+
inlineSize: iconSize,
|
|
86
|
+
blockSize: iconSize,
|
|
87
|
+
aspectRatio: "1",
|
|
88
|
+
objectFit: "contain",
|
|
89
|
+
margin: `calc(${iconSize} * -0.1)`
|
|
90
|
+
})
|
|
91
|
+
}) : null, /* @__PURE__ */ jsx(Popover.Title, {
|
|
92
|
+
className: css({
|
|
93
|
+
margin: 0,
|
|
94
|
+
minWidth: 0,
|
|
95
|
+
fontSize: "var(--chl-font-size-md)",
|
|
96
|
+
fontWeight: 450,
|
|
97
|
+
color: "var(--chl-color-text-primary)",
|
|
98
|
+
textBox: "trim-both cap alphabetic"
|
|
99
|
+
}),
|
|
100
|
+
children: appName
|
|
101
|
+
})]
|
|
102
|
+
}),
|
|
103
|
+
/* @__PURE__ */ jsx("span", {
|
|
104
|
+
className: css({
|
|
105
|
+
fontSize: "var(--chl-font-size-xs)",
|
|
106
|
+
color: "var(--chl-color-text-tertiary)"
|
|
107
|
+
}),
|
|
108
|
+
children: formatActivityDuration(startedAt, now)
|
|
109
|
+
})
|
|
110
|
+
]
|
|
111
|
+
}), poweredBy ? /* @__PURE__ */ jsxs("a", {
|
|
112
|
+
href: "https://chimeling.app",
|
|
113
|
+
target: "_blank",
|
|
114
|
+
rel: "noopener noreferrer",
|
|
115
|
+
"aria-label": "Powered by Chimeling",
|
|
116
|
+
className: css({
|
|
117
|
+
display: "flex",
|
|
118
|
+
alignItems: "center",
|
|
119
|
+
gap: "var(--chl-spacing-2xs)",
|
|
120
|
+
paddingBlock: "var(--chl-spacing-xs)",
|
|
121
|
+
paddingInline: "var(--chl-spacing-sm)",
|
|
122
|
+
fontSize: "var(--chl-font-size-xs)",
|
|
123
|
+
color: "var(--chl-color-text-tertiary)",
|
|
124
|
+
backgroundColor: "var(--chl-color-background-secondary)",
|
|
125
|
+
textDecoration: "none",
|
|
126
|
+
outline: "none",
|
|
127
|
+
"&:hover, &:focus-visible": { backgroundColor: "var(--chl-color-background-secondary-focus)" },
|
|
128
|
+
"&:active": { backgroundColor: "var(--chl-color-background-secondary-active)" }
|
|
129
|
+
}),
|
|
130
|
+
children: ["Powered by ", /* @__PURE__ */ jsx(Logo, {})]
|
|
131
|
+
}) : null]
|
|
30
132
|
})
|
|
31
|
-
}) });
|
|
133
|
+
}) }) });
|
|
32
134
|
}
|
|
33
135
|
//#endregion
|
|
34
|
-
export { ChimelingPopover };
|
|
136
|
+
export { ChimelingPopover, DEFAULT_POPOVER };
|
|
35
137
|
|
|
36
138
|
//# sourceMappingURL=popover.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"popover.js","names":[],"sources":["../../src/components/popover.tsx"],"sourcesContent":["'use client'\n\nimport { Popover } from '@base-ui/react/popover'\nimport type { PopoverPopupProps } from '@base-ui/react/popover'\nimport { formatActivityDuration } from '../lib/format-activity-duration'\nimport { iconImageUrl } from '../lib/icon-url'\nimport { useWidgetContext } from '../lib/widget-context'\nimport Logo from './logo'\n\n// TODO: decide whether to expose the rest of Base UI Popup props.\nexport type ChimelingPopoverProps = Pick<PopoverPopupProps, 'className' | '
|
|
1
|
+
{"version":3,"file":"popover.js","names":[],"sources":["../../src/components/popover.tsx"],"sourcesContent":["'use client'\n\nimport { ClassNames } from '@emotion/react'\nimport { Popover } from '@base-ui/react/popover'\nimport type { PopoverPopupProps } from '@base-ui/react/popover'\nimport { formatActivityDuration } from '../lib/format-activity-duration'\nimport { iconImageUrl } from '../lib/icon-url'\nimport { useWidgetContext } from '../lib/widget-context'\nimport Logo from './logo'\n\n// TODO: decide whether to expose the rest of Base UI Popup props.\nexport type ChimelingPopoverProps = Pick<PopoverPopupProps, 'style'> & {\n className?: string\n ring?: boolean\n shadow?: 'none' | 'subtle' | 'elevated'\n minWidth?: number\n gerundCapitalize?: boolean\n gerundEllipsis?: boolean\n}\n\nexport const DEFAULT_POPOVER = {\n ring: true,\n shadow: 'elevated',\n minWidth: 320,\n gerundCapitalize: true,\n gerundEllipsis: true,\n} as const\n\nconst iconSize = 'calc(22px * var(--chl-font-size-scaling, 1))'\n\nexport function ChimelingPopover({\n className,\n style,\n ring = DEFAULT_POPOVER.ring,\n shadow = DEFAULT_POPOVER.shadow,\n minWidth = DEFAULT_POPOVER.minWidth,\n gerundCapitalize = DEFAULT_POPOVER.gerundCapitalize,\n gerundEllipsis = DEFAULT_POPOVER.gerundEllipsis,\n}: ChimelingPopoverProps) {\n const { showable, now, poweredBy, placement, baseUrl } = useWidgetContext()\n\n if (!showable) {\n return null\n }\n\n const { gerund, appName, iconHash, startedAt } = showable.activity\n\n return (\n <ClassNames>\n {({ css, cx }) => (\n <Popover.Portal>\n {/* TODO: decide whether to expose the rest of Base UI Positioner props. */}\n <Popover.Positioner\n side={placement.side}\n align={placement.align}\n sideOffset={placement.sideOffset}\n >\n <Popover.Popup\n className={cx(\n 'chl-popover',\n css({\n boxSizing: 'border-box',\n display: 'flex',\n flexDirection: 'column',\n minWidth,\n overflow: 'clip',\n padding: 0,\n margin: 0,\n outline: 'none',\n color: 'var(--chl-color-text-primary)',\n backgroundColor: 'var(--chl-color-background-primary)',\n borderRadius: 'var(--chl-border-radius-lg)',\n border: 'none',\n boxShadow:\n [\n ...(shadow === 'subtle' ? ['var(--chl-shadow-subtle)'] : []),\n ...(shadow === 'elevated' ? ['var(--chl-shadow-elevated)'] : []),\n ...(ring ? ['var(--chl-ring)'] : []),\n ].join(', ') || 'none',\n }),\n className,\n )}\n style={style}\n data-ring={ring ? 'true' : 'false'}\n data-shadow={shadow}\n data-gerund-capitalize={gerundCapitalize ? 'true' : 'false'}\n data-gerund-ellipsis={gerundEllipsis ? 'true' : 'false'}\n >\n <div\n className={css({\n display: 'flex',\n flexDirection: 'column',\n gap: 'var(--chl-spacing-2xs)',\n padding: 'var(--chl-spacing-sm)',\n })}\n >\n <Popover.Description\n className={css({\n margin: 0,\n fontSize: 'var(--chl-font-size-sm)',\n fontWeight: 400,\n color: 'var(--chl-color-text-tertiary)',\n '[data-gerund-capitalize=\"true\"] &::first-letter': {\n textTransform: 'uppercase',\n },\n '[data-gerund-ellipsis=\"true\"] &::after': {\n content: '\"...\"',\n },\n })}\n >\n {gerund}\n </Popover.Description>\n <div\n className={css({\n display: 'flex',\n alignItems: 'center',\n gap: 'var(--chl-spacing-2xs)',\n minWidth: 0,\n })}\n >\n {iconHash ? (\n <img\n src={iconImageUrl(baseUrl, iconHash)}\n alt=\"\"\n width={24}\n height={24}\n className={css({\n display: 'block',\n flex: '0 0 auto',\n inlineSize: iconSize,\n blockSize: iconSize,\n aspectRatio: '1',\n objectFit: 'contain',\n margin: `calc(${iconSize} * -0.1)`,\n })}\n />\n ) : null}\n <Popover.Title\n className={css({\n margin: 0,\n minWidth: 0,\n fontSize: 'var(--chl-font-size-md)',\n fontWeight: 450,\n color: 'var(--chl-color-text-primary)',\n textBox: 'trim-both cap alphabetic',\n })}\n >\n {appName}\n </Popover.Title>\n </div>\n <span\n className={css({\n fontSize: 'var(--chl-font-size-xs)',\n color: 'var(--chl-color-text-tertiary)',\n })}\n >\n {formatActivityDuration(startedAt, now)}\n </span>\n </div>\n {poweredBy ? (\n <a\n href=\"https://chimeling.app\"\n target=\"_blank\"\n rel=\"noopener noreferrer\"\n aria-label=\"Powered by Chimeling\"\n className={css({\n display: 'flex',\n alignItems: 'center',\n gap: 'var(--chl-spacing-2xs)',\n paddingBlock: 'var(--chl-spacing-xs)',\n paddingInline: 'var(--chl-spacing-sm)',\n fontSize: 'var(--chl-font-size-xs)',\n color: 'var(--chl-color-text-tertiary)',\n backgroundColor: 'var(--chl-color-background-secondary)',\n textDecoration: 'none',\n outline: 'none',\n '&:hover, &:focus-visible': {\n backgroundColor: 'var(--chl-color-background-secondary-focus)',\n },\n '&:active': {\n backgroundColor: 'var(--chl-color-background-secondary-active)',\n },\n })}\n >\n Powered by <Logo />\n </a>\n ) : null}\n </Popover.Popup>\n </Popover.Positioner>\n </Popover.Portal>\n )}\n </ClassNames>\n )\n}\n"],"mappings":"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"}
|
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
import { ChimelingColorScheme } from "../theme/tokens.js";
|
|
2
|
+
import "../theme/index.js";
|
|
1
3
|
import { ReactNode } from "react";
|
|
2
4
|
//#region src/components/provider.d.ts
|
|
3
5
|
type ChimelingProviderProps = {
|
|
@@ -5,8 +7,13 @@ type ChimelingProviderProps = {
|
|
|
5
7
|
refreshInterval?: number;
|
|
6
8
|
children?: ReactNode;
|
|
7
9
|
nonce?: string;
|
|
10
|
+
accentColor?: string;
|
|
11
|
+
colorScheme?: ChimelingColorScheme;
|
|
12
|
+
spacingScaling?: number;
|
|
13
|
+
fontSizeScaling?: number;
|
|
14
|
+
borderRadiusScaling?: number;
|
|
8
15
|
};
|
|
9
|
-
declare function ChimelingProvider({ baseUrl, refreshInterval, children, nonce }: ChimelingProviderProps): import("react").JSX.Element;
|
|
16
|
+
declare function ChimelingProvider({ baseUrl, refreshInterval, children, nonce, accentColor, colorScheme, spacingScaling, fontSizeScaling, borderRadiusScaling }: ChimelingProviderProps): import("react").JSX.Element;
|
|
10
17
|
//#endregion
|
|
11
18
|
export { ChimelingProvider, ChimelingProviderProps };
|
|
12
19
|
//# sourceMappingURL=provider.d.ts.map
|
|
@@ -1,36 +1,71 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import { DEFAULT_PRESENCE_REFRESH_INTERVAL } from "../lib/config.js";
|
|
3
3
|
import { ChimelingContext } from "../lib/context.js";
|
|
4
|
+
import { useClientCommitted } from "../lib/use-client-committed.js";
|
|
5
|
+
import { generateContrastColor } from "../theme/color-system.js";
|
|
6
|
+
import { rootStyle } from "../theme/tokens.js";
|
|
7
|
+
import { ThemeProvider } from "../theme/context.js";
|
|
8
|
+
import "../theme/index.js";
|
|
4
9
|
import { useMemo } from "react";
|
|
5
10
|
import { createClient, createConfig } from "@cairntale/chimeling-js/client";
|
|
6
11
|
import createCache from "@emotion/cache";
|
|
7
|
-
import { CacheProvider } from "@emotion/react";
|
|
8
|
-
import { jsx } from "react/jsx-runtime";
|
|
12
|
+
import { CacheProvider, Global } from "@emotion/react";
|
|
13
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
9
14
|
//#region src/components/provider.tsx
|
|
10
|
-
|
|
15
|
+
const DEFAULT_BASE_URL = "https://chimeling.app";
|
|
16
|
+
function ChimelingProvider({ baseUrl, refreshInterval = DEFAULT_PRESENCE_REFRESH_INTERVAL, children, nonce, accentColor, colorScheme, spacingScaling, fontSizeScaling, borderRadiusScaling }) {
|
|
17
|
+
const committed = useClientCommitted();
|
|
11
18
|
const client = useMemo(() => createClient(createConfig({ baseUrl: baseUrl ?? "https://chimeling.app" })), [baseUrl]);
|
|
12
19
|
const value = useMemo(() => ({
|
|
13
20
|
client,
|
|
14
21
|
refreshInterval
|
|
15
22
|
}), [client, refreshInterval]);
|
|
23
|
+
const theme = useMemo(() => {
|
|
24
|
+
if (accentColor !== void 0) generateContrastColor(accentColor);
|
|
25
|
+
return {
|
|
26
|
+
accentColor,
|
|
27
|
+
colorScheme,
|
|
28
|
+
spacingScaling,
|
|
29
|
+
fontSizeScaling,
|
|
30
|
+
borderRadiusScaling
|
|
31
|
+
};
|
|
32
|
+
}, [
|
|
33
|
+
accentColor,
|
|
34
|
+
colorScheme,
|
|
35
|
+
spacingScaling,
|
|
36
|
+
fontSizeScaling,
|
|
37
|
+
borderRadiusScaling
|
|
38
|
+
]);
|
|
16
39
|
const emotionCache = useMemo(() => {
|
|
17
|
-
|
|
40
|
+
if (!committed) return;
|
|
41
|
+
const insertionPoint = document.querySelector(`style#chl-style-insertion-point`) ?? void 0;
|
|
18
42
|
return createCache({
|
|
19
43
|
key: "chl-internal",
|
|
20
44
|
prepend: !insertionPoint,
|
|
21
45
|
insertionPoint,
|
|
22
46
|
nonce
|
|
23
47
|
});
|
|
24
|
-
}, [nonce]);
|
|
25
|
-
|
|
26
|
-
value
|
|
27
|
-
children: /* @__PURE__ */ jsx(
|
|
28
|
-
value,
|
|
29
|
-
children
|
|
48
|
+
}, [committed, nonce]);
|
|
49
|
+
const tree = /* @__PURE__ */ jsx(ChimelingContext.Provider, {
|
|
50
|
+
value,
|
|
51
|
+
children: /* @__PURE__ */ jsx(ThemeProvider, {
|
|
52
|
+
value: theme,
|
|
53
|
+
children: committed ? children : null
|
|
30
54
|
})
|
|
31
55
|
});
|
|
56
|
+
if (!emotionCache) return tree;
|
|
57
|
+
return /* @__PURE__ */ jsxs(CacheProvider, {
|
|
58
|
+
value: emotionCache,
|
|
59
|
+
children: [/* @__PURE__ */ jsx(Global, { styles: {
|
|
60
|
+
":root": rootStyle(theme),
|
|
61
|
+
".chl-trigger, .chl-popover": {
|
|
62
|
+
fontFamily: "var(--chl-font-family)",
|
|
63
|
+
...theme.colorScheme === "light" || theme.colorScheme === "dark" ? { colorScheme: theme.colorScheme } : {}
|
|
64
|
+
}
|
|
65
|
+
} }), tree]
|
|
66
|
+
});
|
|
32
67
|
}
|
|
33
68
|
//#endregion
|
|
34
|
-
export { ChimelingProvider };
|
|
69
|
+
export { ChimelingProvider, DEFAULT_BASE_URL };
|
|
35
70
|
|
|
36
71
|
//# sourceMappingURL=provider.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"provider.js","names":[],"sources":["../../src/components/provider.tsx"],"sourcesContent":["'use client'\n\nimport { useMemo, type ReactNode } from 'react'\nimport { createClient, createConfig } from '@cairntale/chimeling-js/client'\nimport { DEFAULT_PRESENCE_REFRESH_INTERVAL } from '../lib/config'\nimport { ChimelingContext } from '../lib/context'\nimport createCache from '@emotion/cache'\nimport { CacheProvider } from '@emotion/react'\n\nexport type ChimelingProviderProps = {\n baseUrl?: string\n refreshInterval?: number\n children?: ReactNode\n nonce?: string\n}\n\nexport function ChimelingProvider({\n baseUrl,\n refreshInterval = DEFAULT_PRESENCE_REFRESH_INTERVAL,\n children,\n nonce,\n}: ChimelingProviderProps) {\n const client = useMemo(\n () => createClient(createConfig({ baseUrl: baseUrl ??
|
|
1
|
+
{"version":3,"file":"provider.js","names":[],"sources":["../../src/components/provider.tsx"],"sourcesContent":["'use client'\n\nimport { useMemo, type ReactNode } from 'react'\nimport { createClient, createConfig } from '@cairntale/chimeling-js/client'\nimport { DEFAULT_PRESENCE_REFRESH_INTERVAL } from '../lib/config'\nimport { ChimelingContext } from '../lib/context'\nimport { useClientCommitted } from '../lib/use-client-committed'\nimport createCache from '@emotion/cache'\nimport { CacheProvider, Global } from '@emotion/react'\nimport {\n ThemeProvider,\n generateContrastColor,\n rootStyle,\n type ChimelingColorScheme,\n} from '../theme'\n\nexport type ChimelingProviderProps = {\n baseUrl?: string\n refreshInterval?: number\n children?: ReactNode\n nonce?: string\n accentColor?: string\n colorScheme?: ChimelingColorScheme\n spacingScaling?: number\n fontSizeScaling?: number\n borderRadiusScaling?: number\n}\n\nexport const DEFAULT_BASE_URL = 'https://chimeling.app'\n\nexport function ChimelingProvider({\n baseUrl,\n refreshInterval = DEFAULT_PRESENCE_REFRESH_INTERVAL,\n children,\n nonce,\n accentColor,\n colorScheme,\n spacingScaling,\n fontSizeScaling,\n borderRadiusScaling,\n}: ChimelingProviderProps) {\n const committed = useClientCommitted()\n const client = useMemo(\n () => createClient(createConfig({ baseUrl: baseUrl ?? DEFAULT_BASE_URL })),\n [baseUrl],\n )\n const value = useMemo(() => ({ client, refreshInterval }), [client, refreshInterval])\n const theme = useMemo(() => {\n if (accentColor !== undefined) {\n generateContrastColor(accentColor)\n }\n return { accentColor, colorScheme, spacingScaling, fontSizeScaling, borderRadiusScaling }\n }, [accentColor, colorScheme, spacingScaling, fontSizeScaling, borderRadiusScaling])\n\n const emotionCache = useMemo(() => {\n if (!committed) {\n return undefined\n }\n\n const insertionPoint =\n document.querySelector<HTMLElement>(`style#chl-style-insertion-point`) ?? undefined\n\n return createCache({\n key: 'chl-internal',\n prepend: !insertionPoint,\n insertionPoint,\n nonce,\n })\n }, [committed, nonce])\n\n const tree = (\n <ChimelingContext.Provider value={value}>\n <ThemeProvider value={theme}>{committed ? children : null}</ThemeProvider>\n </ChimelingContext.Provider>\n )\n\n if (!emotionCache) {\n return tree\n }\n\n return (\n <CacheProvider value={emotionCache}>\n <Global\n styles={{\n ':root': rootStyle(theme),\n '.chl-trigger, .chl-popover': {\n fontFamily: 'var(--chl-font-family)',\n ...(theme.colorScheme === 'light' || theme.colorScheme === 'dark'\n ? { colorScheme: theme.colorScheme }\n : {}),\n },\n }}\n />\n {tree}\n </CacheProvider>\n )\n}\n"],"mappings":";;;;;;;;;;;;;;AA4BA,MAAa,mBAAmB;AAEhC,SAAgB,kBAAkB,EAChC,SACA,kBAAkB,mCAClB,UACA,OACA,aACA,aACA,gBACA,iBACA,uBACyB;CACzB,MAAM,YAAY,mBAAmB;CACrC,MAAM,SAAS,cACP,aAAa,aAAa,EAAE,SAAS,WAAA,wBAA4B,CAAC,CAAC,GACzE,CAAC,OAAO,CACV;CACA,MAAM,QAAQ,eAAe;EAAE;EAAQ;CAAgB,IAAI,CAAC,QAAQ,eAAe,CAAC;CACpF,MAAM,QAAQ,cAAc;EAC1B,IAAI,gBAAgB,KAAA,GAClB,sBAAsB,WAAW;EAEnC,OAAO;GAAE;GAAa;GAAa;GAAgB;GAAiB;EAAoB;CAC1F,GAAG;EAAC;EAAa;EAAa;EAAgB;EAAiB;CAAmB,CAAC;CAEnF,MAAM,eAAe,cAAc;EACjC,IAAI,CAAC,WACH;EAGF,MAAM,iBACJ,SAAS,cAA2B,iCAAiC,KAAK,KAAA;EAE5E,OAAO,YAAY;GACjB,KAAK;GACL,SAAS,CAAC;GACV;GACA;EACF,CAAC;CACH,GAAG,CAAC,WAAW,KAAK,CAAC;CAErB,MAAM,OACJ,oBAAC,iBAAiB,UAAlB;EAAkC;EAChC,UAAA,oBAAC,eAAD;GAAe,OAAO;GAAQ,UAAA,YAAY,WAAW;EAAoB,CAAA;CAChD,CAAA;CAG7B,IAAI,CAAC,cACH,OAAO;CAGT,OACE,qBAAC,eAAD;EAAe,OAAO;EAAtB,UAAA,CACE,oBAAC,QAAD,EACE,QAAQ;GACN,SAAS,UAAU,KAAK;GACxB,8BAA8B;IAC5B,YAAY;IACZ,GAAI,MAAM,gBAAgB,WAAW,MAAM,gBAAgB,SACvD,EAAE,aAAa,MAAM,YAAY,IACjC,CAAC;GACP;EACF,EACD,CAAA,GACA,IACY;;AAEnB"}
|
package/dist/components/root.js
CHANGED
|
@@ -7,9 +7,13 @@ import { useEffect, useMemo, useRef, useState } from "react";
|
|
|
7
7
|
import { jsx } from "react/jsx-runtime";
|
|
8
8
|
import { Popover } from "@base-ui/react/popover";
|
|
9
9
|
//#region src/components/root.tsx
|
|
10
|
-
const
|
|
11
|
-
|
|
12
|
-
|
|
10
|
+
const DEFAULT_ROOT = {
|
|
11
|
+
openOnHover: false,
|
|
12
|
+
hoverOpenDelay: 300,
|
|
13
|
+
hoverCloseDelay: 0,
|
|
14
|
+
sideOffset: 6
|
|
15
|
+
};
|
|
16
|
+
function ChimelingRoot({ userId, children, poweredBy = true, openOnHover = DEFAULT_ROOT.openOnHover, hoverOpenDelay = DEFAULT_ROOT.hoverOpenDelay, hoverCloseDelay = DEFAULT_ROOT.hoverCloseDelay, onReady, presence: presenceOverride, refreshInterval, side, align, sideOffset = DEFAULT_ROOT.sideOffset }) {
|
|
13
17
|
const { client } = useChimelingContext();
|
|
14
18
|
const fetched = useResolvedUserPresence(presenceOverride === void 0 ? userId : "", { refreshInterval });
|
|
15
19
|
const presence = presenceOverride ?? fetched.data;
|
|
@@ -61,6 +65,6 @@ function ChimelingRoot({ userId, children, poweredBy = true, openOnHover = false
|
|
|
61
65
|
});
|
|
62
66
|
}
|
|
63
67
|
//#endregion
|
|
64
|
-
export { ChimelingRoot };
|
|
68
|
+
export { ChimelingRoot, DEFAULT_ROOT };
|
|
65
69
|
|
|
66
70
|
//# sourceMappingURL=root.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"root.js","names":[],"sources":["../../src/components/root.tsx"],"sourcesContent":["'use client'\n\nimport { useEffect, useMemo, useRef, useState, type ReactNode } from 'react'\nimport { Popover } from '@base-ui/react/popover'\nimport type { GetResolvedUserPresenceResponse } from '@cairntale/chimeling-js'\nimport { useResolvedUserPresence } from '../hooks/use-resolved-user-presence'\nimport { useChimelingContext } from '../lib/context'\nimport { getShowablePresence, type ShowablePresence } from '../lib/showable-presence'\nimport { WidgetContext, type WidgetPlacement } from '../lib/widget-context'\n\
|
|
1
|
+
{"version":3,"file":"root.js","names":[],"sources":["../../src/components/root.tsx"],"sourcesContent":["'use client'\n\nimport { useEffect, useMemo, useRef, useState, type ReactNode } from 'react'\nimport { Popover } from '@base-ui/react/popover'\nimport type { GetResolvedUserPresenceResponse } from '@cairntale/chimeling-js'\nimport { useResolvedUserPresence } from '../hooks/use-resolved-user-presence'\nimport { useChimelingContext } from '../lib/context'\nimport { getShowablePresence, type ShowablePresence } from '../lib/showable-presence'\nimport { WidgetContext, type WidgetPlacement } from '../lib/widget-context'\n\nexport const DEFAULT_ROOT = {\n openOnHover: false,\n hoverOpenDelay: 300,\n hoverCloseDelay: 0,\n sideOffset: 6,\n} as const\n\nexport type ChimelingRootProps = WidgetPlacement & {\n userId: string\n children: ReactNode\n poweredBy?: boolean\n openOnHover?: boolean\n hoverOpenDelay?: number\n hoverCloseDelay?: number\n onReady?: (presence: ShowablePresence) => void\n presence?: GetResolvedUserPresenceResponse\n refreshInterval?: number\n}\n\nexport function ChimelingRoot({\n userId,\n children,\n poweredBy = true,\n openOnHover = DEFAULT_ROOT.openOnHover,\n hoverOpenDelay = DEFAULT_ROOT.hoverOpenDelay,\n hoverCloseDelay = DEFAULT_ROOT.hoverCloseDelay,\n onReady,\n presence: presenceOverride,\n refreshInterval,\n side,\n align,\n sideOffset = DEFAULT_ROOT.sideOffset,\n}: ChimelingRootProps) {\n const { client } = useChimelingContext()\n const fetched = useResolvedUserPresence(presenceOverride === undefined ? userId : '', {\n refreshInterval,\n })\n const presence = presenceOverride ?? fetched.data\n const showable = useMemo(() => getShowablePresence(presence), [presence])\n\n const [now, setNow] = useState(() => new Date())\n const readyRef = useRef(false)\n\n useEffect(() => {\n if (!showable) {\n return\n }\n\n const id = setInterval(() => setNow(new Date()), 1000)\n return () => clearInterval(id)\n }, [showable])\n\n useEffect(() => {\n if (readyRef.current || !showable) {\n return\n }\n\n readyRef.current = true\n onReady?.(showable)\n }, [showable, onReady])\n\n const baseUrl = client.getConfig().baseUrl ?? ''\n const placement = useMemo(() => ({ side, align, sideOffset }), [side, align, sideOffset])\n\n const value = useMemo(\n () => ({\n showable,\n now,\n poweredBy,\n openOnHover,\n hoverOpenDelay,\n hoverCloseDelay,\n placement,\n baseUrl,\n }),\n [showable, now, poweredBy, openOnHover, hoverOpenDelay, hoverCloseDelay, placement, baseUrl],\n )\n\n return (\n <WidgetContext.Provider value={value}>\n {showable ? <Popover.Root>{children}</Popover.Root> : children}\n </WidgetContext.Provider>\n )\n}\n"],"mappings":";;;;;;;;;AAUA,MAAa,eAAe;CAC1B,aAAa;CACb,gBAAgB;CAChB,iBAAiB;CACjB,YAAY;AACd;AAcA,SAAgB,cAAc,EAC5B,QACA,UACA,YAAY,MACZ,cAAc,aAAa,aAC3B,iBAAiB,aAAa,gBAC9B,kBAAkB,aAAa,iBAC/B,SACA,UAAU,kBACV,iBACA,MACA,OACA,aAAa,aAAa,cACL;CACrB,MAAM,EAAE,WAAW,oBAAoB;CACvC,MAAM,UAAU,wBAAwB,qBAAqB,KAAA,IAAY,SAAS,IAAI,EACpF,gBACF,CAAC;CACD,MAAM,WAAW,oBAAoB,QAAQ;CAC7C,MAAM,WAAW,cAAc,oBAAoB,QAAQ,GAAG,CAAC,QAAQ,CAAC;CAExE,MAAM,CAAC,KAAK,UAAU,+BAAe,IAAI,KAAK,CAAC;CAC/C,MAAM,WAAW,OAAO,KAAK;CAE7B,gBAAgB;EACd,IAAI,CAAC,UACH;EAGF,MAAM,KAAK,kBAAkB,uBAAO,IAAI,KAAK,CAAC,GAAG,GAAI;EACrD,aAAa,cAAc,EAAE;CAC/B,GAAG,CAAC,QAAQ,CAAC;CAEb,gBAAgB;EACd,IAAI,SAAS,WAAW,CAAC,UACvB;EAGF,SAAS,UAAU;EACnB,UAAU,QAAQ;CACpB,GAAG,CAAC,UAAU,OAAO,CAAC;CAEtB,MAAM,UAAU,OAAO,UAAU,CAAC,CAAC,WAAW;CAC9C,MAAM,YAAY,eAAe;EAAE;EAAM;EAAO;CAAW,IAAI;EAAC;EAAM;EAAO;CAAU,CAAC;CAExF,MAAM,QAAQ,eACL;EACL;EACA;EACA;EACA;EACA;EACA;EACA;EACA;CACF,IACA;EAAC;EAAU;EAAK;EAAW;EAAa;EAAgB;EAAiB;EAAW;CAAO,CAC7F;CAEA,OACE,oBAAC,cAAc,UAAf;EAA+B;EAC5B,UAAA,WAAW,oBAAC,QAAQ,MAAT,EAAe,SAAuB,CAAA,IAAI;CAChC,CAAA;AAE5B"}
|
|
@@ -1,7 +1,12 @@
|
|
|
1
1
|
import { PopoverTriggerProps } from "@base-ui/react/popover";
|
|
2
2
|
//#region src/components/trigger.d.ts
|
|
3
|
-
type ChimelingTriggerProps = Pick<PopoverTriggerProps, '
|
|
4
|
-
|
|
3
|
+
type ChimelingTriggerProps = Pick<PopoverTriggerProps, 'style' | 'nativeButton' | 'id'> & {
|
|
4
|
+
className?: string;
|
|
5
|
+
variant?: 'inline' | 'pill';
|
|
6
|
+
shimmer?: boolean;
|
|
7
|
+
gradient?: boolean;
|
|
8
|
+
};
|
|
9
|
+
declare function ChimelingTrigger({ className, style, nativeButton, id, variant, shimmer, gradient }: ChimelingTriggerProps): import("react").JSX.Element | null;
|
|
5
10
|
//#endregion
|
|
6
11
|
export { ChimelingTrigger, ChimelingTriggerProps };
|
|
7
12
|
//# sourceMappingURL=trigger.d.ts.map
|
|
@@ -1,23 +1,85 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import { useWidgetContext } from "../lib/widget-context.js";
|
|
3
|
+
import { ClassNames, keyframes } from "@emotion/react";
|
|
3
4
|
import { jsx } from "react/jsx-runtime";
|
|
4
5
|
import { Popover } from "@base-ui/react/popover";
|
|
5
6
|
//#region src/components/trigger.tsx
|
|
6
|
-
|
|
7
|
+
const shimmerAnimation = keyframes({
|
|
8
|
+
from: { backgroundPosition: "200% 0" },
|
|
9
|
+
to: { backgroundPosition: "-200% 0" }
|
|
10
|
+
});
|
|
11
|
+
const triggerReset = {
|
|
12
|
+
border: "none",
|
|
13
|
+
outline: "none",
|
|
14
|
+
margin: 0,
|
|
15
|
+
padding: 0,
|
|
16
|
+
backgroundColor: "unset",
|
|
17
|
+
fontWeight: 450
|
|
18
|
+
};
|
|
19
|
+
const DEFAULT_TRIGGER = {
|
|
20
|
+
variant: "inline",
|
|
21
|
+
shimmer: true,
|
|
22
|
+
gradient: true
|
|
23
|
+
};
|
|
24
|
+
function ChimelingTrigger({ className, style, nativeButton, id, variant = DEFAULT_TRIGGER.variant, shimmer = DEFAULT_TRIGGER.shimmer, gradient = DEFAULT_TRIGGER.gradient }) {
|
|
7
25
|
const { showable, openOnHover, hoverOpenDelay, hoverCloseDelay } = useWidgetContext();
|
|
8
26
|
if (!showable) return null;
|
|
9
|
-
return /* @__PURE__ */ jsx(Popover.Trigger, {
|
|
10
|
-
className,
|
|
27
|
+
return /* @__PURE__ */ jsx(ClassNames, { children: ({ css, cx }) => /* @__PURE__ */ jsx(Popover.Trigger, {
|
|
28
|
+
className: cx("chl-trigger", css({
|
|
29
|
+
...triggerReset,
|
|
30
|
+
"&[data-variant=\"inline\"]": {
|
|
31
|
+
display: "inline",
|
|
32
|
+
fontSize: "inherit",
|
|
33
|
+
...shimmer ? {
|
|
34
|
+
backgroundImage: `linear-gradient(to right, var(--chl-color-background-accent) 0%, color-mix(in oklch, var(--chl-color-background-accent) 60%, #fff) 50%, var(--chl-color-background-accent) 100%)`,
|
|
35
|
+
backgroundSize: "200% 100%",
|
|
36
|
+
backgroundClip: "text",
|
|
37
|
+
WebkitBackgroundClip: "text",
|
|
38
|
+
color: "transparent",
|
|
39
|
+
animation: `${shimmerAnimation} 4s linear infinite`,
|
|
40
|
+
"@media (prefers-reduced-motion: reduce)": { animation: "none" },
|
|
41
|
+
"&:hover, &:focus-visible": { backgroundImage: `linear-gradient(to right, var(--chl-color-background-accent-focus) 0%, color-mix(in oklch, var(--chl-color-background-accent-focus) 60%, #fff) 50%, var(--chl-color-background-accent-focus) 100%)` },
|
|
42
|
+
"&:active": { backgroundImage: `linear-gradient(to right, var(--chl-color-background-accent-active) 0%, color-mix(in oklch, var(--chl-color-background-accent-active) 60%, #fff) 50%, var(--chl-color-background-accent-active) 100%)` }
|
|
43
|
+
} : {
|
|
44
|
+
color: "var(--chl-color-background-accent)",
|
|
45
|
+
"&:hover, &:focus-visible": { color: "var(--chl-color-background-accent-focus)" },
|
|
46
|
+
"&:active": { color: "var(--chl-color-background-accent-active)" }
|
|
47
|
+
}
|
|
48
|
+
},
|
|
49
|
+
"&[data-variant=\"pill\"]": {
|
|
50
|
+
display: "block",
|
|
51
|
+
padding: "var(--chl-spacing-2xs) var(--chl-spacing-xs)",
|
|
52
|
+
borderRadius: "var(--chl-border-radius-full)",
|
|
53
|
+
fontSize: "var(--chl-font-size-sm)",
|
|
54
|
+
color: "var(--chl-color-background-accent-contrast)",
|
|
55
|
+
backgroundImage: gradient ? `linear-gradient(to bottom, color-mix(in oklch, var(--chl-color-background-accent) 80%, #fff), var(--chl-color-background-accent))` : void 0,
|
|
56
|
+
backgroundColor: gradient ? void 0 : "var(--chl-color-background-accent)",
|
|
57
|
+
"&::first-letter": { textTransform: "uppercase" },
|
|
58
|
+
"&:hover, &:focus-visible": {
|
|
59
|
+
color: "var(--chl-color-background-accent-contrast-focus)",
|
|
60
|
+
backgroundImage: gradient ? `linear-gradient(to bottom, color-mix(in oklch, var(--chl-color-background-accent-focus) 80%, #fff), var(--chl-color-background-accent-focus))` : void 0,
|
|
61
|
+
backgroundColor: gradient ? void 0 : "var(--chl-color-background-accent-focus)"
|
|
62
|
+
},
|
|
63
|
+
"&:active": {
|
|
64
|
+
color: "var(--chl-color-background-accent-contrast-active)",
|
|
65
|
+
backgroundImage: gradient ? `linear-gradient(to bottom, color-mix(in oklch, var(--chl-color-background-accent-active) 80%, #fff), var(--chl-color-background-accent-active))` : void 0,
|
|
66
|
+
backgroundColor: gradient ? void 0 : "var(--chl-color-background-accent-active)"
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
}), className),
|
|
11
70
|
style,
|
|
12
71
|
nativeButton,
|
|
13
72
|
id,
|
|
73
|
+
"data-variant": variant,
|
|
74
|
+
"data-shimmer": shimmer ? "true" : "false",
|
|
75
|
+
"data-gradient": gradient ? "true" : "false",
|
|
14
76
|
openOnHover,
|
|
15
77
|
delay: hoverOpenDelay,
|
|
16
78
|
closeDelay: hoverCloseDelay,
|
|
17
79
|
children: showable.activity.gerund
|
|
18
|
-
});
|
|
80
|
+
}) });
|
|
19
81
|
}
|
|
20
82
|
//#endregion
|
|
21
|
-
export { ChimelingTrigger };
|
|
83
|
+
export { ChimelingTrigger, DEFAULT_TRIGGER };
|
|
22
84
|
|
|
23
85
|
//# sourceMappingURL=trigger.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"trigger.js","names":[],"sources":["../../src/components/trigger.tsx"],"sourcesContent":["'use client'\n\nimport { Popover } from '@base-ui/react/popover'\nimport type { PopoverTriggerProps } from '@base-ui/react/popover'\nimport { useWidgetContext } from '../lib/widget-context'\n\n
|
|
1
|
+
{"version":3,"file":"trigger.js","names":[],"sources":["../../src/components/trigger.tsx"],"sourcesContent":["'use client'\n\nimport { ClassNames, keyframes } from '@emotion/react'\nimport { Popover } from '@base-ui/react/popover'\nimport type { PopoverTriggerProps } from '@base-ui/react/popover'\nimport { useWidgetContext } from '../lib/widget-context'\n\nconst shimmerAnimation = keyframes({\n from: { backgroundPosition: '200% 0' },\n to: { backgroundPosition: '-200% 0' },\n})\n\nconst triggerReset = {\n border: 'none',\n outline: 'none',\n margin: 0,\n padding: 0,\n backgroundColor: 'unset',\n fontWeight: 450,\n} as const\n\nexport type ChimelingTriggerProps = Pick<PopoverTriggerProps, 'style' | 'nativeButton' | 'id'> & {\n className?: string\n variant?: 'inline' | 'pill'\n shimmer?: boolean\n gradient?: boolean\n}\n\nexport const DEFAULT_TRIGGER = {\n variant: 'inline',\n shimmer: true,\n gradient: true,\n} as const\n\nexport function ChimelingTrigger({\n className,\n style,\n nativeButton,\n id,\n variant = DEFAULT_TRIGGER.variant,\n shimmer = DEFAULT_TRIGGER.shimmer,\n gradient = DEFAULT_TRIGGER.gradient,\n}: ChimelingTriggerProps) {\n const { showable, openOnHover, hoverOpenDelay, hoverCloseDelay } = useWidgetContext()\n\n if (!showable) {\n return null\n }\n\n return (\n <ClassNames>\n {({ css, cx }) => (\n <Popover.Trigger\n className={cx(\n 'chl-trigger',\n css({\n ...triggerReset,\n '&[data-variant=\"inline\"]': {\n display: 'inline',\n fontSize: 'inherit',\n ...(shimmer\n ? {\n backgroundImage: `linear-gradient(to right, var(--chl-color-background-accent) 0%, color-mix(in oklch, var(--chl-color-background-accent) 60%, #fff) 50%, var(--chl-color-background-accent) 100%)`,\n backgroundSize: '200% 100%',\n backgroundClip: 'text',\n WebkitBackgroundClip: 'text',\n color: 'transparent',\n animation: `${shimmerAnimation} 4s linear infinite`,\n '@media (prefers-reduced-motion: reduce)': {\n animation: 'none',\n },\n '&:hover, &:focus-visible': {\n backgroundImage: `linear-gradient(to right, var(--chl-color-background-accent-focus) 0%, color-mix(in oklch, var(--chl-color-background-accent-focus) 60%, #fff) 50%, var(--chl-color-background-accent-focus) 100%)`,\n },\n '&:active': {\n backgroundImage: `linear-gradient(to right, var(--chl-color-background-accent-active) 0%, color-mix(in oklch, var(--chl-color-background-accent-active) 60%, #fff) 50%, var(--chl-color-background-accent-active) 100%)`,\n },\n }\n : {\n color: 'var(--chl-color-background-accent)',\n '&:hover, &:focus-visible': {\n color: 'var(--chl-color-background-accent-focus)',\n },\n '&:active': {\n color: 'var(--chl-color-background-accent-active)',\n },\n }),\n },\n '&[data-variant=\"pill\"]': {\n display: 'block',\n padding: 'var(--chl-spacing-2xs) var(--chl-spacing-xs)',\n borderRadius: 'var(--chl-border-radius-full)',\n fontSize: 'var(--chl-font-size-sm)',\n color: 'var(--chl-color-background-accent-contrast)',\n backgroundImage: gradient\n ? `linear-gradient(to bottom, color-mix(in oklch, var(--chl-color-background-accent) 80%, #fff), var(--chl-color-background-accent))`\n : undefined,\n backgroundColor: gradient ? undefined : 'var(--chl-color-background-accent)',\n '&::first-letter': {\n textTransform: 'uppercase',\n },\n '&:hover, &:focus-visible': {\n color: 'var(--chl-color-background-accent-contrast-focus)',\n backgroundImage: gradient\n ? `linear-gradient(to bottom, color-mix(in oklch, var(--chl-color-background-accent-focus) 80%, #fff), var(--chl-color-background-accent-focus))`\n : undefined,\n backgroundColor: gradient\n ? undefined\n : 'var(--chl-color-background-accent-focus)',\n },\n '&:active': {\n color: 'var(--chl-color-background-accent-contrast-active)',\n backgroundImage: gradient\n ? `linear-gradient(to bottom, color-mix(in oklch, var(--chl-color-background-accent-active) 80%, #fff), var(--chl-color-background-accent-active))`\n : undefined,\n backgroundColor: gradient\n ? undefined\n : 'var(--chl-color-background-accent-active)',\n },\n },\n }),\n className,\n )}\n style={style}\n nativeButton={nativeButton}\n id={id}\n data-variant={variant}\n data-shimmer={shimmer ? 'true' : 'false'}\n data-gradient={gradient ? 'true' : 'false'}\n openOnHover={openOnHover}\n delay={hoverOpenDelay}\n closeDelay={hoverCloseDelay}\n >\n {showable.activity.gerund}\n </Popover.Trigger>\n )}\n </ClassNames>\n )\n}\n"],"mappings":";;;;;;AAOA,MAAM,mBAAmB,UAAU;CACjC,MAAM,EAAE,oBAAoB,SAAS;CACrC,IAAI,EAAE,oBAAoB,UAAU;AACtC,CAAC;AAED,MAAM,eAAe;CACnB,QAAQ;CACR,SAAS;CACT,QAAQ;CACR,SAAS;CACT,iBAAiB;CACjB,YAAY;AACd;AASA,MAAa,kBAAkB;CAC7B,SAAS;CACT,SAAS;CACT,UAAU;AACZ;AAEA,SAAgB,iBAAiB,EAC/B,WACA,OACA,cACA,IACA,UAAU,gBAAgB,SAC1B,UAAU,gBAAgB,SAC1B,WAAW,gBAAgB,YACH;CACxB,MAAM,EAAE,UAAU,aAAa,gBAAgB,oBAAoB,iBAAiB;CAEpF,IAAI,CAAC,UACH,OAAO;CAGT,OACE,oBAAC,YAAD,EAAA,WACI,EAAE,KAAK,SACP,oBAAC,QAAQ,SAAT;EACE,WAAW,GACT,eACA,IAAI;GACF,GAAG;GACH,8BAA4B;IAC1B,SAAS;IACT,UAAU;IACV,GAAI,UACA;KACE,iBAAiB;KACjB,gBAAgB;KAChB,gBAAgB;KAChB,sBAAsB;KACtB,OAAO;KACP,WAAW,GAAG,iBAAiB;KAC/B,2CAA2C,EACzC,WAAW,OACb;KACA,4BAA4B,EAC1B,iBAAiB,qMACnB;KACA,YAAY,EACV,iBAAiB,wMACnB;IACF,IACA;KACE,OAAO;KACP,4BAA4B,EAC1B,OAAO,2CACT;KACA,YAAY,EACV,OAAO,4CACT;IACF;GACN;GACA,4BAA0B;IACxB,SAAS;IACT,SAAS;IACT,cAAc;IACd,UAAU;IACV,OAAO;IACP,iBAAiB,WACb,sIACA,KAAA;IACJ,iBAAiB,WAAW,KAAA,IAAY;IACxC,mBAAmB,EACjB,eAAe,YACjB;IACA,4BAA4B;KAC1B,OAAO;KACP,iBAAiB,WACb,kJACA,KAAA;KACJ,iBAAiB,WACb,KAAA,IACA;IACN;IACA,YAAY;KACV,OAAO;KACP,iBAAiB,WACb,oJACA,KAAA;KACJ,iBAAiB,WACb,KAAA,IACA;IACN;GACF;EACF,CAAC,GACD,SACF;EACO;EACO;EACV;EACJ,gBAAc;EACd,gBAAc,UAAU,SAAS;EACjC,iBAAe,WAAW,SAAS;EACtB;EACb,OAAO;EACP,YAAY;EAEX,UAAA,SAAS,SAAS;CACJ,CAAA,EAET,CAAA;AAEhB"}
|
package/dist/index.d.ts
CHANGED
|
@@ -4,7 +4,7 @@ import { ChimelingRoot, ChimelingRootProps } from "./components/root.js";
|
|
|
4
4
|
import { ChimelingTrigger, ChimelingTriggerProps } from "./components/trigger.js";
|
|
5
5
|
import { ChimelingPopover, ChimelingPopoverProps } from "./components/popover.js";
|
|
6
6
|
import { Chimeling } from "./components/chimeling.js";
|
|
7
|
-
import { ChimelingPlayground } from "./components/playground/playground.js";
|
|
7
|
+
import { ChimelingPlayground, ChimelingPlaygroundProps } from "./components/playground/playground.js";
|
|
8
8
|
import "./components/index.js";
|
|
9
9
|
import { useChimelingClient } from "./hooks/use-client.js";
|
|
10
10
|
import { useResolvedUserPresence } from "./hooks/use-resolved-user-presence.js";
|
|
@@ -12,4 +12,4 @@ import "./hooks/index.js";
|
|
|
12
12
|
import { formatActivityDuration } from "./lib/format-activity-duration.js";
|
|
13
13
|
import { iconImageUrl } from "./lib/icon-url.js";
|
|
14
14
|
import "./lib/index.js";
|
|
15
|
-
export { Chimeling, ChimelingPlayground, ChimelingPopover, type ChimelingPopoverProps, ChimelingProvider, type ChimelingProviderProps, ChimelingRoot, type ChimelingRootProps, ChimelingTrigger, type ChimelingTriggerProps, type PresenceActivity, type ShowablePresence, formatActivityDuration, getShowablePresence, iconImageUrl, useChimelingClient, useResolvedUserPresence };
|
|
15
|
+
export { Chimeling, ChimelingPlayground, type ChimelingPlaygroundProps, ChimelingPopover, type ChimelingPopoverProps, ChimelingProvider, type ChimelingProviderProps, ChimelingRoot, type ChimelingRootProps, ChimelingTrigger, type ChimelingTriggerProps, type PresenceActivity, type ShowablePresence, formatActivityDuration, getShowablePresence, iconImageUrl, useChimelingClient, useResolvedUserPresence };
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { useSyncExternalStore } from "react";
|
|
3
|
+
//#region src/lib/use-client-committed.ts
|
|
4
|
+
const subscribe = () => () => {};
|
|
5
|
+
const getSnapshot = () => true;
|
|
6
|
+
const getServerSnapshot = () => false;
|
|
7
|
+
/** False on the server and during hydration; true after the client commits. */
|
|
8
|
+
function useClientCommitted() {
|
|
9
|
+
return useSyncExternalStore(subscribe, getSnapshot, getServerSnapshot);
|
|
10
|
+
}
|
|
11
|
+
//#endregion
|
|
12
|
+
export { useClientCommitted };
|
|
13
|
+
|
|
14
|
+
//# sourceMappingURL=use-client-committed.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-client-committed.js","names":[],"sources":["../../src/lib/use-client-committed.ts"],"sourcesContent":["'use client'\n\nimport { useSyncExternalStore } from 'react'\n\nconst subscribe = () => () => {}\nconst getSnapshot = () => true\nconst getServerSnapshot = () => false\n\n/** False on the server and during hydration; true after the client commits. */\nexport function useClientCommitted() {\n return useSyncExternalStore(subscribe, getSnapshot, getServerSnapshot)\n}\n"],"mappings":";;;AAIA,MAAM,wBAAwB,CAAC;AAC/B,MAAM,oBAAoB;AAC1B,MAAM,0BAA0B;;AAGhC,SAAgB,qBAAqB;CACnC,OAAO,qBAAqB,WAAW,aAAa,iBAAiB;AACvE"}
|
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
import "./showable-presence.js";
|
|
2
2
|
import { PopoverPositionerProps } from "@base-ui/react/popover";
|
|
3
3
|
//#region src/lib/widget-context.d.ts
|
|
4
|
-
type WidgetPlacement = Pick<PopoverPositionerProps, 'side' | 'align'
|
|
4
|
+
type WidgetPlacement = Pick<PopoverPositionerProps, 'side' | 'align'> & {
|
|
5
|
+
sideOffset?: number;
|
|
6
|
+
};
|
|
5
7
|
//#endregion
|
|
6
8
|
export { WidgetPlacement };
|
|
7
9
|
//# sourceMappingURL=widget-context.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"widget-context.js","names":[],"sources":["../../src/lib/widget-context.ts"],"sourcesContent":["'use client'\n\nimport { createContext, useContext } from 'react'\nimport type { PopoverPositionerProps } from '@base-ui/react/popover'\nimport { packageErrorMessage } from './config'\nimport type { ShowablePresence } from './showable-presence'\n\nexport type WidgetPlacement = Pick<PopoverPositionerProps, 'side' | 'align'
|
|
1
|
+
{"version":3,"file":"widget-context.js","names":[],"sources":["../../src/lib/widget-context.ts"],"sourcesContent":["'use client'\n\nimport { createContext, useContext } from 'react'\nimport type { PopoverPositionerProps } from '@base-ui/react/popover'\nimport { packageErrorMessage } from './config'\nimport type { ShowablePresence } from './showable-presence'\n\nexport type WidgetPlacement = Pick<PopoverPositionerProps, 'side' | 'align'> & {\n sideOffset?: number\n}\n\nexport type WidgetContextValue = {\n showable: ShowablePresence | null\n now: Date\n poweredBy: boolean\n openOnHover: boolean\n hoverOpenDelay: number\n hoverCloseDelay: number\n placement: WidgetPlacement\n baseUrl: string\n}\n\nexport const WidgetContext = createContext<WidgetContextValue | null>(null)\n\nexport function useWidgetContext(): WidgetContextValue {\n const context = useContext(WidgetContext)\n if (!context) {\n throw new Error(\n packageErrorMessage(\n 'This component can only be used within the <Chimeling.Root /> component.',\n ),\n )\n }\n return context\n}\n"],"mappings":";;;;AAsBA,MAAa,gBAAgB,cAAyC,IAAI;AAE1E,SAAgB,mBAAuC;CACrD,MAAM,UAAU,WAAW,aAAa;CACxC,IAAI,CAAC,SACH,MAAM,IAAI,MACR,oBACE,0EACF,CACF;CAEF,OAAO;AACT"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import "@emotion/react";
|