@seamly/web-ui 24.4.1 → 24.5.0-beta.1
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/dist/lib/index.debug.js +272 -154
- package/build/dist/lib/index.debug.js.map +1 -1
- package/build/dist/lib/index.debug.min.js +1 -1
- package/build/dist/lib/index.debug.min.js.LICENSE.txt +11 -5
- package/build/dist/lib/index.debug.min.js.map +1 -1
- package/build/dist/lib/index.js +226 -112
- package/build/dist/lib/index.js.map +1 -1
- package/build/dist/lib/index.min.js +1 -1
- package/build/dist/lib/index.min.js.map +1 -1
- package/build/dist/lib/style-guide.js +170 -57
- package/build/dist/lib/style-guide.js.map +1 -1
- package/build/dist/lib/style-guide.min.js +1 -1
- package/build/dist/lib/style-guide.min.js.map +1 -1
- package/package.json +20 -19
- package/src/javascripts/core/config.types.ts +1 -0
- package/src/javascripts/core/domains/config/slice.ts +2 -0
- package/src/javascripts/core/domains/store/slice.ts +0 -1
- package/src/javascripts/core/ui/components/conversation/conversation.tsx +5 -1
- package/src/javascripts/core/ui/components/core/seamly-new-notifications.ts +2 -49
- package/src/javascripts/core/ui/components/entry/text-entry/hooks.ts +7 -2
- package/src/javascripts/core/ui/components/layout/chat.tsx +10 -1
- package/src/javascripts/core/ui/components/options/transcript/transcript-form.tsx +1 -0
- package/src/stylesheets/2-tools/_functions.scss +2 -2
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@seamly/web-ui",
|
|
3
|
-
"version": "24.
|
|
3
|
+
"version": "24.5.0-beta.1",
|
|
4
4
|
"main": "build/dist/lib/index.js",
|
|
5
5
|
"types": "build/src/javascripts/index.d.ts",
|
|
6
6
|
"exports": {
|
|
@@ -21,9 +21,9 @@
|
|
|
21
21
|
"webpack/*"
|
|
22
22
|
],
|
|
23
23
|
"dependencies": {
|
|
24
|
-
"@reduxjs/toolkit": "^2.
|
|
24
|
+
"@reduxjs/toolkit": "^2.8.1",
|
|
25
25
|
"@ultraq/icu-message-formatter": "^0.14.3",
|
|
26
|
-
"core-js": "^3.
|
|
26
|
+
"core-js": "^3.42.0",
|
|
27
27
|
"focus-trap": "^7.6.4",
|
|
28
28
|
"include-media": "^2.0.0",
|
|
29
29
|
"js-cookie": "^3.0.5",
|
|
@@ -32,11 +32,11 @@
|
|
|
32
32
|
"reconnecting-websocket": "^4.4.0"
|
|
33
33
|
},
|
|
34
34
|
"devDependencies": {
|
|
35
|
-
"@babel/core": "^7.
|
|
36
|
-
"@babel/preset-env": "^7.
|
|
37
|
-
"@babel/preset-react": "^7.
|
|
38
|
-
"@babel/preset-typescript": "^7.27.
|
|
39
|
-
"@playwright/test": "
|
|
35
|
+
"@babel/core": "^7.27.1",
|
|
36
|
+
"@babel/preset-env": "^7.27.2",
|
|
37
|
+
"@babel/preset-react": "^7.27.1",
|
|
38
|
+
"@babel/preset-typescript": "^7.27.1",
|
|
39
|
+
"@playwright/test": "1.51.1",
|
|
40
40
|
"@seamly/doc-site": "^4.0.0",
|
|
41
41
|
"@seamly/eslint-config": "^3.1.0",
|
|
42
42
|
"@seamly/prettier-config": "^3.1.0",
|
|
@@ -45,22 +45,22 @@
|
|
|
45
45
|
"@testing-library/preact": "^3.2.4",
|
|
46
46
|
"@types/core-js": "^2.5.8",
|
|
47
47
|
"@types/jest": "^29.5.12",
|
|
48
|
-
"@typescript-eslint/eslint-plugin": "^8.
|
|
49
|
-
"@typescript-eslint/parser": "^8.
|
|
48
|
+
"@typescript-eslint/eslint-plugin": "^8.32.0",
|
|
49
|
+
"@typescript-eslint/parser": "^8.32.0",
|
|
50
50
|
"babel-jest": "^29.7.0",
|
|
51
51
|
"babel-loader": "^10.0.0",
|
|
52
52
|
"copy-webpack-plugin": "^13.0.0",
|
|
53
53
|
"eslint": "^8.57.0",
|
|
54
54
|
"eslint-config-prettier": "^9.1.0",
|
|
55
|
-
"eslint-import-resolver-typescript": "^3.
|
|
55
|
+
"eslint-import-resolver-typescript": "^3.10.1",
|
|
56
56
|
"eslint-plugin-filenames": "^1.3.2",
|
|
57
57
|
"eslint-plugin-import": "^2.29.1",
|
|
58
58
|
"eslint-plugin-jest": "^28.11.0",
|
|
59
|
-
"eslint-plugin-prettier": "^5.
|
|
60
|
-
"eslint-plugin-react": "^7.37.
|
|
59
|
+
"eslint-plugin-prettier": "^5.4.0",
|
|
60
|
+
"eslint-plugin-react": "^7.37.5",
|
|
61
61
|
"eslint-plugin-react-hooks": "^4.6.2",
|
|
62
62
|
"file-loader": "^6.2.0",
|
|
63
|
-
"fork-ts-checker-webpack-plugin": "^9.0
|
|
63
|
+
"fork-ts-checker-webpack-plugin": "^9.1.0",
|
|
64
64
|
"husky": "^9.1.7",
|
|
65
65
|
"jest": "^29.7.0",
|
|
66
66
|
"jest-environment-jsdom": "^29.7.0",
|
|
@@ -69,23 +69,24 @@
|
|
|
69
69
|
"openapi-typescript": "^6.7",
|
|
70
70
|
"playwright-test-coverage": "^1.2.12",
|
|
71
71
|
"postcss": "^8.5.3",
|
|
72
|
-
"preact": "^10.26.
|
|
72
|
+
"preact": "^10.26.6",
|
|
73
73
|
"prettier": "^3.5.3",
|
|
74
74
|
"rimraf": "^6.0.1",
|
|
75
75
|
"style-loader": "^4.0.0",
|
|
76
|
-
"stylelint": "^16.
|
|
77
|
-
"typescript": "^5.8.
|
|
78
|
-
"webpack": "^5.
|
|
76
|
+
"stylelint": "^16.19.1",
|
|
77
|
+
"typescript": "^5.8.3",
|
|
78
|
+
"webpack": "^5.99.8",
|
|
79
79
|
"webpack-bundle-analyzer": "^4.10.2",
|
|
80
80
|
"webpack-cli": "^6.0.1",
|
|
81
81
|
"webpack-dev-server": "^5.2.1",
|
|
82
82
|
"webpack-merge": "^6.0.1"
|
|
83
83
|
},
|
|
84
84
|
"resolutions": {
|
|
85
|
+
"sass": "1.79.6",
|
|
85
86
|
"string-width": "^4.2.3"
|
|
86
87
|
},
|
|
87
88
|
"peerDependencies": {
|
|
88
|
-
"preact": "^10.
|
|
89
|
+
"preact": "^10.26.6"
|
|
89
90
|
},
|
|
90
91
|
"scripts": {
|
|
91
92
|
"build:clean": "rimraf build; mkdir -p build",
|
|
@@ -104,6 +104,7 @@ export type Config = Partial<Omit<ChannelConfig, 'preChat'>> & {
|
|
|
104
104
|
connectWhenInView: boolean
|
|
105
105
|
visibilityCallback?: VisibilityCallback
|
|
106
106
|
errorCallback?: ErrorCallback
|
|
107
|
+
alwaysShowEntryLabel?: boolean
|
|
107
108
|
api: ApiConfig
|
|
108
109
|
appContainerClassNames?: string[] | ((_config: Config) => string[])
|
|
109
110
|
zIndex?: number
|
|
@@ -7,6 +7,7 @@ import type { ChannelEvent } from 'domains/store/store.types'
|
|
|
7
7
|
|
|
8
8
|
export const initialConfigState: Config = {
|
|
9
9
|
...defaultConfig,
|
|
10
|
+
alwaysShowEntryLabel: false,
|
|
10
11
|
api: {
|
|
11
12
|
domain: '',
|
|
12
13
|
key: '',
|
|
@@ -37,6 +38,7 @@ export const initialConfigState: Config = {
|
|
|
37
38
|
}
|
|
38
39
|
|
|
39
40
|
const configKeys: (keyof Config)[] = [
|
|
41
|
+
'alwaysShowEntryLabel',
|
|
40
42
|
'hideOnNoUserResponse',
|
|
41
43
|
'connectWhenInView',
|
|
42
44
|
'showDisclaimer',
|
|
@@ -79,7 +79,11 @@ const Conversation = () => {
|
|
|
79
79
|
<div className={className('chat__body')}>
|
|
80
80
|
<div className={className('conversation__container')}>
|
|
81
81
|
<PrivacyDisclaimer />
|
|
82
|
-
<ol
|
|
82
|
+
<ol
|
|
83
|
+
className={className('conversation')}
|
|
84
|
+
role="log"
|
|
85
|
+
aria-label={t('chat.srLabel')}
|
|
86
|
+
>
|
|
83
87
|
<ComponentFilter>
|
|
84
88
|
<Events />
|
|
85
89
|
</ComponentFilter>
|
|
@@ -1,58 +1,11 @@
|
|
|
1
|
-
import { useEffect
|
|
2
|
-
import { newMessageScreenReaderWait } from 'config'
|
|
1
|
+
import { useEffect } from 'preact/hooks'
|
|
3
2
|
import { useI18n } from 'domains/i18n/hooks'
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
useEvents,
|
|
7
|
-
useLiveRegion,
|
|
8
|
-
useSeamlyIsHistoryLoaded,
|
|
9
|
-
} from 'ui/hooks/seamly-hooks'
|
|
10
|
-
import { debounce } from 'ui/utils/general-utils'
|
|
3
|
+
import { useLiveRegion, useSeamlyIsHistoryLoaded } from 'ui/hooks/seamly-hooks'
|
|
11
4
|
|
|
12
5
|
const SeamlyNewNotifications = () => {
|
|
13
6
|
const { t } = useI18n()
|
|
14
|
-
const events = useEvents()
|
|
15
|
-
const previousEventCount = useRef(0)
|
|
16
|
-
const previousServerEventCount = useRef(0)
|
|
17
7
|
const isHistoryLoaded = useSeamlyIsHistoryLoaded()
|
|
18
8
|
const { sendPolite } = useLiveRegion()
|
|
19
|
-
const { isOpen } = useVisibility()
|
|
20
|
-
const prevIsOpen = useRef(null)
|
|
21
|
-
const debounceFunc = useRef<
|
|
22
|
-
((_runInstant?: boolean | undefined) => void) | null
|
|
23
|
-
>(null)
|
|
24
|
-
|
|
25
|
-
const notifyUnread = useMemo(() => {
|
|
26
|
-
return debounce((eventArray) => {
|
|
27
|
-
const serverEventCount = eventArray.filter(
|
|
28
|
-
({ payload }) => !payload.fromClient && !payload.fromHistory,
|
|
29
|
-
).length
|
|
30
|
-
if (serverEventCount > previousServerEventCount.current) {
|
|
31
|
-
sendPolite(
|
|
32
|
-
t('message.srNewEventCount', {
|
|
33
|
-
newCount: serverEventCount - previousServerEventCount.current,
|
|
34
|
-
}),
|
|
35
|
-
)
|
|
36
|
-
previousServerEventCount.current = serverEventCount
|
|
37
|
-
}
|
|
38
|
-
}, newMessageScreenReaderWait)
|
|
39
|
-
}, [sendPolite, t])
|
|
40
|
-
|
|
41
|
-
useEffect(() => {
|
|
42
|
-
if (events.length > previousEventCount.current) {
|
|
43
|
-
if (isOpen) {
|
|
44
|
-
debounceFunc.current = notifyUnread(events)
|
|
45
|
-
}
|
|
46
|
-
previousEventCount.current = events.length
|
|
47
|
-
}
|
|
48
|
-
}, [events, notifyUnread, isOpen])
|
|
49
|
-
|
|
50
|
-
useEffect(() => {
|
|
51
|
-
if (prevIsOpen.current && !isOpen && debounceFunc.current) {
|
|
52
|
-
debounceFunc.current(true)
|
|
53
|
-
debounceFunc.current = null
|
|
54
|
-
}
|
|
55
|
-
}, [isOpen])
|
|
56
9
|
|
|
57
10
|
useEffect(() => {
|
|
58
11
|
if (isHistoryLoaded) {
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { useEffect, useMemo } from 'preact/hooks'
|
|
2
2
|
import { maxCharacterSrDebounceDelay, maxCharacterWarningLimit } from 'config'
|
|
3
|
+
import { useConfig } from 'domains/config/hooks'
|
|
3
4
|
import { useFormControl } from 'domains/forms/hooks'
|
|
4
5
|
import { useI18n } from 'domains/i18n/hooks'
|
|
5
6
|
import { useAppDispatch } from 'domains/store'
|
|
@@ -62,6 +63,7 @@ export const useEntryTextTranslation = (controlName: 'textMessageEntry') => {
|
|
|
62
63
|
entryMeta: { optionsOverride },
|
|
63
64
|
} = useSeamlyStateContext()
|
|
64
65
|
|
|
66
|
+
const { alwaysShowEntryLabel } = useConfig()
|
|
65
67
|
const { t } = useI18n()
|
|
66
68
|
|
|
67
69
|
const placeholder: string = useMemo(
|
|
@@ -89,8 +91,11 @@ export const useEntryTextTranslation = (controlName: 'textMessageEntry') => {
|
|
|
89
91
|
)
|
|
90
92
|
|
|
91
93
|
const labelClass = useMemo(
|
|
92
|
-
() =>
|
|
93
|
-
|
|
94
|
+
() =>
|
|
95
|
+
alwaysShowEntryLabel === true || optionsOverride?.text?.label
|
|
96
|
+
? 'label'
|
|
97
|
+
: 'visually-hidden',
|
|
98
|
+
[alwaysShowEntryLabel, optionsOverride?.text?.label],
|
|
94
99
|
)
|
|
95
100
|
|
|
96
101
|
return { placeholder, label, labelClass }
|
|
@@ -9,6 +9,7 @@ import { className } from 'lib/css'
|
|
|
9
9
|
import Suggestions from 'ui/components/suggestions'
|
|
10
10
|
import { useSeamlyAppContainerClassNames } from 'ui/hooks/component-helper-hooks'
|
|
11
11
|
import { useSeamlyLayoutMode } from 'ui/hooks/seamly-state-hooks'
|
|
12
|
+
import { useGeneratedId } from 'ui/hooks/utility-hooks'
|
|
12
13
|
|
|
13
14
|
const Chat = forwardRef<
|
|
14
15
|
HTMLElement,
|
|
@@ -18,6 +19,7 @@ const Chat = forwardRef<
|
|
|
18
19
|
const { namespace, layoutMode } = useConfig()
|
|
19
20
|
const { isInline } = useSeamlyLayoutMode()
|
|
20
21
|
const appContainerClassNames = useSeamlyAppContainerClassNames()
|
|
22
|
+
const headingId = useGeneratedId()
|
|
21
23
|
const userHasResponded = useUserHasResponded()
|
|
22
24
|
const { t } = useI18n()
|
|
23
25
|
|
|
@@ -55,8 +57,15 @@ const Chat = forwardRef<
|
|
|
55
57
|
onKeyDown={onKeyDownHandler}
|
|
56
58
|
tabIndex={-1}
|
|
57
59
|
ref={forwardedRef}
|
|
58
|
-
|
|
60
|
+
role={layoutMode === 'window' ? 'dialog' : undefined}
|
|
61
|
+
aria-labelledby={headingId}
|
|
59
62
|
>
|
|
63
|
+
<h2
|
|
64
|
+
className={className('chat__title', 'visually-hidden')}
|
|
65
|
+
id={headingId}
|
|
66
|
+
>
|
|
67
|
+
{t('chat.srLabel')}
|
|
68
|
+
</h2>
|
|
60
69
|
<div className={className('chat-wrapper')}>{children}</div>
|
|
61
70
|
{layoutMode === 'inline' && isOpen && <Suggestions isAside={true} />}
|
|
62
71
|
</section>
|
|
@@ -11,6 +11,7 @@ export default function TranscriptForm({ controlName, describedById }) {
|
|
|
11
11
|
id="email-id"
|
|
12
12
|
name={controlName}
|
|
13
13
|
type="email"
|
|
14
|
+
autocomplete="email"
|
|
14
15
|
className={className('transcript__input')}
|
|
15
16
|
aria-describedby={describedById}
|
|
16
17
|
labelClass={className('label')}
|
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
/** SET TEXT COLOR */
|
|
4
4
|
@function set-text-color($color) {
|
|
5
|
-
@if color.
|
|
5
|
+
@if color.channel($color, 'lightness', $space: hsl) > 66.66 {
|
|
6
6
|
@return $grey-e;
|
|
7
7
|
} @else {
|
|
8
8
|
@return $white;
|
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
|
|
12
12
|
/** SET BORDER COLOR */
|
|
13
13
|
@function set-border-color($color) {
|
|
14
|
-
@if color.
|
|
14
|
+
@if color.channel($color, 'lightness', $space: hsl) > 66.66 {
|
|
15
15
|
@return $grey-c;
|
|
16
16
|
} @else {
|
|
17
17
|
@return $white;
|