@skatteetaten/ds-overlays 1.4.0 → 1.5.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/Modal/index.esm.js +48 -5
- package/PopoverContent.esm.js +1 -1
- package/RolePicker/index.esm.d.ts +1 -0
- package/RolePicker/index.esm.js +196 -0
- package/RolePicker/styles.css +1 -0
- package/RolePickerBusinessList/index.esm.d.ts +1 -0
- package/RolePickerBusinessList/index.esm.js +225 -0
- package/RolePickerBusinessList/styles.css +1 -0
- package/RolePickerContext/index.esm.d.ts +1 -0
- package/RolePickerContext/index.esm.js +5 -0
- package/RolePickerFilterInput/index.esm.d.ts +1 -0
- package/RolePickerFilterInput/index.esm.js +109 -0
- package/RolePickerFilterInput/styles.css +1 -0
- package/RolePickerPeopleList/index.esm.d.ts +1 -0
- package/RolePickerPeopleList/index.esm.js +96 -0
- package/RolePickerPeopleList/styles.css +1 -0
- package/RolePickerRow/index.esm.d.ts +1 -0
- package/RolePickerRow/index.esm.js +43 -0
- package/RolePickerRow/styles.css +1 -0
- package/index.esm.js +9 -0
- package/package.json +11 -7
- package/src/Modal/Modal.types.d.ts +8 -1
- package/src/RolePicker/RolePicker.d.ts +4 -0
- package/src/RolePicker/RolePicker.types.d.ts +57 -0
- package/src/RolePicker/defaults.d.ts +3 -0
- package/src/RolePickerBusinessList/RolePickerBusinessList.d.ts +5 -0
- package/src/RolePickerBusinessList/RolePickerBusinessList.types.d.ts +7 -0
- package/src/RolePickerContext/RolePickerContext.d.ts +2 -0
- package/src/RolePickerFilterInput/RolePickerFilterInput.d.ts +2 -0
- package/src/RolePickerFilterInput/RolePickerFilterInput.types.d.ts +7 -0
- package/src/RolePickerPeopleList/RolePickerPeopleList.d.ts +2 -0
- package/src/RolePickerPeopleList/RolePickerPeopleList.types.d.ts +5 -0
- package/src/RolePickerRow/RolePickerRow.d.ts +6 -0
- package/src/RolePickerRow/RolePickerRow.types.d.ts +4 -0
- package/src/index.d.ts +2 -0
package/Modal/index.esm.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { jsx, jsxs } from 'react/jsx-runtime';
|
|
2
|
-
import { forwardRef, useId, useRef, useImperativeHandle, useEffect } from 'react';
|
|
2
|
+
import { forwardRef, useId, useRef, useImperativeHandle, useState, useEffect } from 'react';
|
|
3
3
|
import { useTranslation } from 'react-i18next';
|
|
4
4
|
import { IconButton } from '@skatteetaten/ds-buttons';
|
|
5
5
|
import { dsI18n, SkatteetatenLogo, Separator, getCommonClassNameDefault } from '@skatteetaten/ds-core-utils';
|
|
@@ -31,8 +31,7 @@ var styles = {
|
|
|
31
31
|
"srOnly": "Modal-module_srOnly__W8dQv"
|
|
32
32
|
};
|
|
33
33
|
|
|
34
|
-
const Modal = /*#__PURE__*/ forwardRef(({ id, className = getCommonClassNameDefault(), classNames, lang, 'data-testid': dataTestId, dismissOnEsc = getModalDismissOnEscDefault(), dismissOnOutsideClick = getModalDismissOnOutsideClickDefault(), hideCloseButton, hideTitle, imageSource, imageSourceAltText, padding = getModalPaddingDefault(), title, variant = getModalVariantDefault(),
|
|
35
|
-
shadowRootNode, onClose, children }, ref)=>{
|
|
34
|
+
const Modal = /*#__PURE__*/ forwardRef(({ id, className = getCommonClassNameDefault(), classNames, lang, 'data-testid': dataTestId, dismissOnEsc = getModalDismissOnEscDefault(), dismissOnOutsideClick = getModalDismissOnOutsideClickDefault(), hideCloseButton, hideTitle, imageSource, imageSourceAltText, padding = getModalPaddingDefault(), title, variant = getModalVariantDefault(), shadowRootNode, onClose, renderIcon, children }, ref)=>{
|
|
36
35
|
const headingId = `modalHeadingId-${useId()}`;
|
|
37
36
|
const { t } = useTranslation('ds_overlays', {
|
|
38
37
|
i18n: dsI18n
|
|
@@ -42,6 +41,46 @@ shadowRootNode, onClose, children }, ref)=>{
|
|
|
42
41
|
});
|
|
43
42
|
const modalRef = useRef(null);
|
|
44
43
|
useImperativeHandle(ref, ()=>modalRef?.current);
|
|
44
|
+
const [isAutoOpened, setIsAutoOpened] = useState();
|
|
45
|
+
useEffect(()=>{
|
|
46
|
+
const dialog = modalRef.current;
|
|
47
|
+
if (dialog) {
|
|
48
|
+
const originalMethod = dialog.showModal;
|
|
49
|
+
dialog.showModal = function showModal(...args) {
|
|
50
|
+
setIsAutoOpened(document.activeElement?.nodeName === 'BODY');
|
|
51
|
+
originalMethod.apply(dialog, args);
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
}, []);
|
|
55
|
+
useEffect(()=>{
|
|
56
|
+
const dialog = modalRef.current;
|
|
57
|
+
const handleClose = ()=>{
|
|
58
|
+
if (isAutoOpened) {
|
|
59
|
+
setIsAutoOpened(false);
|
|
60
|
+
//TODO skiplink kan ligge i shadowDom. Da kan vi ikke finne den med querySelector
|
|
61
|
+
// Denne modalen kan også eksistere i en shadowDom. ;-)
|
|
62
|
+
const skipLink = document.querySelector('a[data-skip-link]');
|
|
63
|
+
if (skipLink) {
|
|
64
|
+
skipLink?.focus();
|
|
65
|
+
} else {
|
|
66
|
+
const prevTabIndex = document.body.tabIndex;
|
|
67
|
+
document.body.tabIndex = -1;
|
|
68
|
+
document.body.focus();
|
|
69
|
+
document.body.tabIndex = prevTabIndex;
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
};
|
|
73
|
+
if (dialog) {
|
|
74
|
+
dialog.addEventListener('close', handleClose);
|
|
75
|
+
}
|
|
76
|
+
return ()=>{
|
|
77
|
+
if (dialog) {
|
|
78
|
+
dialog.removeEventListener('close', handleClose);
|
|
79
|
+
}
|
|
80
|
+
};
|
|
81
|
+
}, [
|
|
82
|
+
isAutoOpened
|
|
83
|
+
]);
|
|
45
84
|
useEffect(()=>{
|
|
46
85
|
/**
|
|
47
86
|
* Hvis konsument endrer children i en åpen modal, vil fokus settes til body og dismissOnEsc vil slutte å fungere.
|
|
@@ -54,10 +93,10 @@ shadowRootNode, onClose, children }, ref)=>{
|
|
|
54
93
|
dismissOnEsc
|
|
55
94
|
]);
|
|
56
95
|
const isClickOutside = (event)=>{
|
|
57
|
-
if (!(event.
|
|
96
|
+
if (!(event.currentTarget instanceof HTMLElement)) {
|
|
58
97
|
return true;
|
|
59
98
|
}
|
|
60
|
-
const rect = event.
|
|
99
|
+
const rect = event.currentTarget.getBoundingClientRect();
|
|
61
100
|
return rect.left > event.clientX || rect.right < event.clientX || rect.top > event.clientY || rect.bottom < event.clientY;
|
|
62
101
|
};
|
|
63
102
|
const handleMouseEvent = (event)=>{
|
|
@@ -94,6 +133,7 @@ shadowRootNode, onClose, children }, ref)=>{
|
|
|
94
133
|
if (e.key === 'Escape') {
|
|
95
134
|
if (dismissOnEsc) {
|
|
96
135
|
onClose?.();
|
|
136
|
+
modalRef.current?.close();
|
|
97
137
|
} else {
|
|
98
138
|
e.preventDefault();
|
|
99
139
|
}
|
|
@@ -125,6 +165,9 @@ shadowRootNode, onClose, children }, ref)=>{
|
|
|
125
165
|
variant === 'important' && /*#__PURE__*/ jsx(SkatteetatenLogo, {
|
|
126
166
|
className: styles.modalLogo
|
|
127
167
|
}),
|
|
168
|
+
renderIcon && /*#__PURE__*/ jsx("div", {
|
|
169
|
+
children: renderIcon?.()
|
|
170
|
+
}),
|
|
128
171
|
/*#__PURE__*/ jsx(Heading, {
|
|
129
172
|
className: `${styles.modalHeading} ${headingNoPaddingClassName} ${hideTitleClassName}`.trim(),
|
|
130
173
|
id: headingId,
|
package/PopoverContent.esm.js
CHANGED
|
@@ -28,7 +28,7 @@ var styles = {
|
|
|
28
28
|
"popoverArrow_right": "PopoverContent-module_popoverArrow_right__MPxU2"
|
|
29
29
|
};
|
|
30
30
|
|
|
31
|
-
const PopoverContent = /*#__PURE__*/ forwardRef(({ id, className = getCommonClassNameDefault(), lang, 'data-testid': dataTestId, children }, ref)=>{
|
|
31
|
+
/* eslint-disable react/forbid-dom-props */ const PopoverContent = /*#__PURE__*/ forwardRef(({ id, className = getCommonClassNameDefault(), lang, 'data-testid': dataTestId, children }, ref)=>{
|
|
32
32
|
const { floatingData, interactions, arrowRef, isOpen, setIsOpen, color = getPopoverColorDefault(), shouldRestoreFocus = getPopoverRestoreFocusDefault(), onClose } = useContext(PopoverContext);
|
|
33
33
|
const { refs, floatingStyles, placement, middlewareData } = floatingData;
|
|
34
34
|
const { getFloatingProps } = interactions;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./src/RolePicker/RolePicker";
|
|
@@ -0,0 +1,196 @@
|
|
|
1
|
+
import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
|
|
2
|
+
import { forwardRef, useState, useDeferredValue, useRef, useImperativeHandle, useMemo } from 'react';
|
|
3
|
+
import { useTranslation } from 'react-i18next';
|
|
4
|
+
import { Button } from '@skatteetaten/ds-buttons';
|
|
5
|
+
import { dsI18n, getCommonClassNameDefault } from '@skatteetaten/ds-core-utils';
|
|
6
|
+
import { FavoriteSVGpath, LogOutSVGpath } from '@skatteetaten/ds-icons';
|
|
7
|
+
import { Paragraph } from '@skatteetaten/ds-typography';
|
|
8
|
+
import { Modal, getModalDismissOnEscDefault, getModalDismissOnOutsideClickDefault } from '../Modal/index.esm.js';
|
|
9
|
+
import { RolePickerBusinessList } from '../RolePickerBusinessList/index.esm.js';
|
|
10
|
+
import { RolePickerContext } from '../RolePickerContext/index.esm.js';
|
|
11
|
+
import { RolePickerFilterInput } from '../RolePickerFilterInput/index.esm.js';
|
|
12
|
+
import { RolePickerPeopleList } from '../RolePickerPeopleList/index.esm.js';
|
|
13
|
+
import { RolePickerRow } from '../RolePickerRow/index.esm.js';
|
|
14
|
+
import '@skatteetaten/ds-forms';
|
|
15
|
+
import '@skatteetaten/ds-navigation';
|
|
16
|
+
import '@skatteetaten/ds-status';
|
|
17
|
+
import './styles.css';
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
const getRolePickerHideCloseButtonDefault = ()=>false;
|
|
21
|
+
const getRolePickerShowSubunitsDefault = ()=>true;
|
|
22
|
+
const getRolePickerShowInactiveBusinessesDefault = ()=>false;
|
|
23
|
+
|
|
24
|
+
var styles = {
|
|
25
|
+
"rolePicker": "RolePicker-module_rolePicker__pTz4X",
|
|
26
|
+
"rolePickerFooter": "RolePicker-module_rolePickerFooter__64Pj-",
|
|
27
|
+
"container": "RolePicker-module_container__VtHRL",
|
|
28
|
+
"showMoreButton": "RolePicker-module_showMoreButton__rY5m5",
|
|
29
|
+
"srOnly": "RolePicker-module_srOnly__ePXta"
|
|
30
|
+
};
|
|
31
|
+
|
|
32
|
+
const RolePicker = /*#__PURE__*/ forwardRef(({ id, className = getCommonClassNameDefault(), lang, 'data-testid': dataTestId, me, businesses, people, title, dismissOnEsc = getModalDismissOnEscDefault(), dismissOnOutsideClick = getModalDismissOnOutsideClickDefault(), hideCloseButton = getRolePickerHideCloseButtonDefault(), showInactiveBusinesses = getRolePickerShowInactiveBusinessesDefault(), showSubunits = getRolePickerShowSubunitsDefault(), onClose, onEntitySelect, onLogout, children }, ref)=>{
|
|
33
|
+
const [filter, setFilter] = useState('');
|
|
34
|
+
const [loadingEntityId, setLoadingEntityId] = useState(undefined);
|
|
35
|
+
const [error, setError] = useState(undefined);
|
|
36
|
+
const { t } = useTranslation('ds_overlays', {
|
|
37
|
+
i18n: dsI18n
|
|
38
|
+
});
|
|
39
|
+
const deferredFilter = useDeferredValue(filter);
|
|
40
|
+
const businessesCount = businesses ? businesses.total : 0;
|
|
41
|
+
const peopleCount = people ? people.total : 0;
|
|
42
|
+
const displaySearch = businessesCount + peopleCount > 10;
|
|
43
|
+
const modalRef = useRef(null);
|
|
44
|
+
useImperativeHandle(ref, ()=>modalRef.current);
|
|
45
|
+
const handleClose = ()=>{
|
|
46
|
+
setError(undefined);
|
|
47
|
+
setLoadingEntityId(undefined);
|
|
48
|
+
onClose?.();
|
|
49
|
+
};
|
|
50
|
+
const getRepresentationText = ()=>{
|
|
51
|
+
if (people && people.total > 0 && businesses && businesses.total > 0) {
|
|
52
|
+
return /*#__PURE__*/ jsxs(Paragraph, {
|
|
53
|
+
children: [
|
|
54
|
+
t('rolepicker.YouCanRepresent'),
|
|
55
|
+
/*#__PURE__*/ jsx("strong", {
|
|
56
|
+
children: ` ${people.total} ${people.total > 1 ? t('rolepicker.People') : t('rolepicker.Person')} ${t('rolepicker.And')} ${businesses.total} ${businesses.total > 1 ? t('rolepicker.Businesses') : t('rolepicker.Business')}.`
|
|
57
|
+
})
|
|
58
|
+
]
|
|
59
|
+
});
|
|
60
|
+
} else if (people && people.total > 0) {
|
|
61
|
+
return /*#__PURE__*/ jsxs(Paragraph, {
|
|
62
|
+
children: [
|
|
63
|
+
t('rolepicker.YouCanRepresent'),
|
|
64
|
+
/*#__PURE__*/ jsx("strong", {
|
|
65
|
+
children: ` ${people.total} ${people.total > 1 ? t('rolepicker.People') : t('rolepicker.Person')}.`
|
|
66
|
+
})
|
|
67
|
+
]
|
|
68
|
+
});
|
|
69
|
+
} else if (businesses && businesses.total > 0) {
|
|
70
|
+
return /*#__PURE__*/ jsxs(Paragraph, {
|
|
71
|
+
children: [
|
|
72
|
+
t('rolepicker.YouCanRepresent'),
|
|
73
|
+
/*#__PURE__*/ jsx("strong", {
|
|
74
|
+
children: ` ${businesses.total} ${businesses.total > 1 ? t('rolepicker.Businesses') : t('rolepicker.Business')}.`
|
|
75
|
+
})
|
|
76
|
+
]
|
|
77
|
+
});
|
|
78
|
+
} else {
|
|
79
|
+
return null;
|
|
80
|
+
}
|
|
81
|
+
};
|
|
82
|
+
const concatenatedClassName = `${styles.container} ${className}`.trim();
|
|
83
|
+
const noValidBusinesses = !me && !people && (!businesses || businesses.total === 0);
|
|
84
|
+
let internalTitle = title ? title : t('rolepicker.Heading');
|
|
85
|
+
if (noValidBusinesses) {
|
|
86
|
+
internalTitle = t('rolepicker.NoBusinessesErrorTitle');
|
|
87
|
+
}
|
|
88
|
+
const contextValue = useMemo(()=>({
|
|
89
|
+
onEntitySelect,
|
|
90
|
+
error,
|
|
91
|
+
setError,
|
|
92
|
+
loadingEntityId,
|
|
93
|
+
setLoadingEntityId
|
|
94
|
+
}), [
|
|
95
|
+
error,
|
|
96
|
+
loadingEntityId,
|
|
97
|
+
onEntitySelect
|
|
98
|
+
]);
|
|
99
|
+
return /*#__PURE__*/ jsx(RolePickerContext.Provider, {
|
|
100
|
+
value: contextValue,
|
|
101
|
+
children: /*#__PURE__*/ jsx(Modal, {
|
|
102
|
+
ref: modalRef,
|
|
103
|
+
id: id,
|
|
104
|
+
className: concatenatedClassName,
|
|
105
|
+
lang: lang,
|
|
106
|
+
title: internalTitle,
|
|
107
|
+
"data-testid": dataTestId,
|
|
108
|
+
dismissOnEsc: dismissOnEsc,
|
|
109
|
+
dismissOnOutsideClick: dismissOnOutsideClick,
|
|
110
|
+
hideCloseButton: hideCloseButton,
|
|
111
|
+
onClose: handleClose,
|
|
112
|
+
children: /*#__PURE__*/ jsxs("div", {
|
|
113
|
+
children: [
|
|
114
|
+
/*#__PURE__*/ jsxs("div", {
|
|
115
|
+
className: styles.rolePicker,
|
|
116
|
+
children: [
|
|
117
|
+
me ? /*#__PURE__*/ jsx(RolePickerRow, {
|
|
118
|
+
id: me.personId,
|
|
119
|
+
title: t('rolepicker.MeHeading'),
|
|
120
|
+
description: `${t('rolepicker.PeopleDescriptionPrefix')} ${me.personId}`,
|
|
121
|
+
svgPath: FavoriteSVGpath,
|
|
122
|
+
titleAs: 'h2',
|
|
123
|
+
onClick: ()=>{
|
|
124
|
+
setLoadingEntityId(me.personId);
|
|
125
|
+
onEntitySelect?.(me).then((res)=>{
|
|
126
|
+
if (res?.error) {
|
|
127
|
+
setError({
|
|
128
|
+
entityId: me.personId,
|
|
129
|
+
message: res.error
|
|
130
|
+
});
|
|
131
|
+
}
|
|
132
|
+
setLoadingEntityId(undefined);
|
|
133
|
+
});
|
|
134
|
+
}
|
|
135
|
+
}) : null,
|
|
136
|
+
getRepresentationText(),
|
|
137
|
+
displaySearch ? /*#__PURE__*/ jsx(RolePickerFilterInput, {
|
|
138
|
+
label: people && businesses ? t('rolepicker.SearchAll') : people ? t('rolepicker.SearchPeople') : t('rolepicker.SearchBusinesses'),
|
|
139
|
+
value: filter,
|
|
140
|
+
onChange: (e)=>setFilter(e.target.value),
|
|
141
|
+
onClear: ()=>setFilter('')
|
|
142
|
+
}) : null,
|
|
143
|
+
people && people?.total > 0 ? /*#__PURE__*/ jsx(RolePickerPeopleList, {
|
|
144
|
+
people: people,
|
|
145
|
+
filterQuery: deferredFilter
|
|
146
|
+
}) : null,
|
|
147
|
+
businesses && businesses.total > 0 ? /*#__PURE__*/ jsx(RolePickerBusinessList, {
|
|
148
|
+
businesses: businesses,
|
|
149
|
+
filterQuery: deferredFilter,
|
|
150
|
+
showSubunits: showSubunits,
|
|
151
|
+
showInactiveBusinesses: showInactiveBusinesses
|
|
152
|
+
}) : null,
|
|
153
|
+
noValidBusinesses ? /*#__PURE__*/ jsxs(Paragraph, {
|
|
154
|
+
children: [
|
|
155
|
+
t('rolepicker.NoBusinessesDescription'),
|
|
156
|
+
' ',
|
|
157
|
+
/*#__PURE__*/ jsxs("strong", {
|
|
158
|
+
children: [
|
|
159
|
+
t('rolepicker.Business'),
|
|
160
|
+
'.'
|
|
161
|
+
]
|
|
162
|
+
})
|
|
163
|
+
]
|
|
164
|
+
}) : null,
|
|
165
|
+
children
|
|
166
|
+
]
|
|
167
|
+
}),
|
|
168
|
+
/*#__PURE__*/ jsx("div", {
|
|
169
|
+
className: styles.rolePickerFooter,
|
|
170
|
+
children: noValidBusinesses ? /*#__PURE__*/ jsx(Button, {
|
|
171
|
+
href: `https://skatt.skatteetaten.no/web/minside/person`,
|
|
172
|
+
children: t('rolepicker.GoToMyPage')
|
|
173
|
+
}) : /*#__PURE__*/ jsxs(Fragment, {
|
|
174
|
+
children: [
|
|
175
|
+
/*#__PURE__*/ jsx(Button, {
|
|
176
|
+
variant: 'secondary',
|
|
177
|
+
svgPath: LogOutSVGpath,
|
|
178
|
+
onClick: onLogout,
|
|
179
|
+
children: t('rolepicker.Logout')
|
|
180
|
+
}),
|
|
181
|
+
!hideCloseButton ? /*#__PURE__*/ jsx(Button, {
|
|
182
|
+
variant: 'secondary',
|
|
183
|
+
onClick: ()=>modalRef.current?.close(),
|
|
184
|
+
children: t('rolepicker.Cancel')
|
|
185
|
+
}) : null
|
|
186
|
+
]
|
|
187
|
+
})
|
|
188
|
+
})
|
|
189
|
+
]
|
|
190
|
+
})
|
|
191
|
+
})
|
|
192
|
+
});
|
|
193
|
+
});
|
|
194
|
+
RolePicker.displayName = 'RolePicker';
|
|
195
|
+
|
|
196
|
+
export { RolePicker, getRolePickerHideCloseButtonDefault, getRolePickerShowInactiveBusinessesDefault, getRolePickerShowSubunitsDefault };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
html:has(dialog[open]){overflow:hidden}.RolePicker-module_rolePicker__pTz4X{display:flex;flex-direction:column;gap:var(--spacing-xl);margin-bottom:var(--spacing-xl)}.RolePicker-module_rolePickerFooter__64Pj-{align-items:center;display:flex;gap:var(--spacing-s)}.RolePicker-module_container__VtHRL{margin-top:var(--spacing-xl);width:var(--container-s)}.RolePicker-module_showMoreButton__rY5m5{text-align:right}.RolePicker-module_srOnly__ePXta{clip:rect(0,0,0,0);border:0;height:1px;margin:-1px;overflow:hidden;padding:0;position:absolute;white-space:nowrap;width:1px}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./src/RolePickerBusinessList/RolePickerBusinessList";
|
|
@@ -0,0 +1,225 @@
|
|
|
1
|
+
import { jsxs, jsx, Fragment } from 'react/jsx-runtime';
|
|
2
|
+
import { useContext, useState, useRef, useMemo, useCallback } from 'react';
|
|
3
|
+
import { useTranslation } from 'react-i18next';
|
|
4
|
+
import { Button } from '@skatteetaten/ds-buttons';
|
|
5
|
+
import { dsI18n } from '@skatteetaten/ds-core-utils';
|
|
6
|
+
import { Checkbox } from '@skatteetaten/ds-forms';
|
|
7
|
+
import { BriefcaseOffSVGpath, BriefcaseMultipleSVGpath, BriefcaseSVGpath } from '@skatteetaten/ds-icons';
|
|
8
|
+
import { Heading } from '@skatteetaten/ds-typography';
|
|
9
|
+
import { RolePickerContext } from '../RolePickerContext/index.esm.js';
|
|
10
|
+
import { RolePickerRow } from '../RolePickerRow/index.esm.js';
|
|
11
|
+
import '@skatteetaten/ds-navigation';
|
|
12
|
+
import '@skatteetaten/ds-status';
|
|
13
|
+
import './styles.css';
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
var styles = {
|
|
17
|
+
"businessList": "RolePickerBusinessList-module_businessList__15fne",
|
|
18
|
+
"checkboxGroup": "RolePickerBusinessList-module_checkboxGroup__cdE2w",
|
|
19
|
+
"showAllButtonWrapper": "RolePickerBusinessList-module_showAllButtonWrapper__ZffHt",
|
|
20
|
+
"subUnitsList": "RolePickerBusinessList-module_subUnitsList__bDv87",
|
|
21
|
+
"subUnit": "RolePickerBusinessList-module_subUnit__DIX6O"
|
|
22
|
+
};
|
|
23
|
+
|
|
24
|
+
const MAX_INITIAL_ITEMS = 5;
|
|
25
|
+
const RolePickerBusinessList = ({ businesses, filterQuery, showInactiveBusinesses: externalShowInactiveBusinesses, showSubunits: externalShowSubUnits })=>{
|
|
26
|
+
const { t } = useTranslation('ds_overlays', {
|
|
27
|
+
i18n: dsI18n
|
|
28
|
+
});
|
|
29
|
+
const ctx = useContext(RolePickerContext);
|
|
30
|
+
const [showAll, setShowAll] = useState(false);
|
|
31
|
+
const [showInactiveBusinesses, setShowInactiveBusinesses] = useState(externalShowInactiveBusinesses);
|
|
32
|
+
const [showSubUnits, setShowSubUnits] = useState(externalShowSubUnits);
|
|
33
|
+
const navRef = useRef(null);
|
|
34
|
+
const handleShowAll = ()=>{
|
|
35
|
+
const visibleLinks = navRef.current?.querySelectorAll('a').length ?? 1;
|
|
36
|
+
setShowAll(true);
|
|
37
|
+
navRef.current?.querySelectorAll('a')[visibleLinks - 1].focus();
|
|
38
|
+
};
|
|
39
|
+
const handleEntityClicked = async (entity)=>{
|
|
40
|
+
ctx?.setLoadingEntityId(entity.organizationNumber);
|
|
41
|
+
ctx?.onEntitySelect?.(entity).then((res)=>{
|
|
42
|
+
if (res?.error) {
|
|
43
|
+
ctx?.setError({
|
|
44
|
+
entityId: entity.organizationNumber,
|
|
45
|
+
message: res.error
|
|
46
|
+
});
|
|
47
|
+
}
|
|
48
|
+
ctx.setLoadingEntityId(undefined);
|
|
49
|
+
});
|
|
50
|
+
};
|
|
51
|
+
const visibleItems = useMemo(()=>{
|
|
52
|
+
// lager en dyp kopiering av business-listen for å unngå mutasjon
|
|
53
|
+
let items = JSON.parse(JSON.stringify(businesses.list));
|
|
54
|
+
items = !showInactiveBusinesses ? items.filter((p)=>!p.isDeleted) : items;
|
|
55
|
+
if (filterQuery) {
|
|
56
|
+
// Filteret sjekker om `filterQuery` er til stede i organisasjonens navn, enhetstype eller organisasjonsnummer.
|
|
57
|
+
// Hvis `showSubUnits` er sann, sjekker det også om noen av underenhetenes navn inkluderer `filterQuery`.
|
|
58
|
+
items = items.filter((business)=>{
|
|
59
|
+
const mainMatch = (business.name + business.unitType).toLowerCase().includes(filterQuery.toLowerCase()) || business.organizationNumber.includes(filterQuery.toLowerCase()) || business.mainOrganizationNumber?.includes(filterQuery.toLowerCase());
|
|
60
|
+
const subunitMatch = showSubUnits && business.subunits?.some((sub)=>(sub.name.toLowerCase() + sub.unitType.toLowerCase()).includes(filterQuery.toLowerCase()) && (showInactiveBusinesses || !sub.isDeleted));
|
|
61
|
+
if (mainMatch) {
|
|
62
|
+
return true;
|
|
63
|
+
}
|
|
64
|
+
if (subunitMatch) {
|
|
65
|
+
const filteredSubunits = business.subunits?.filter((sub)=>(sub.name.toLowerCase() + sub.unitType.toLowerCase()).includes(filterQuery.toLowerCase()) && (showInactiveBusinesses || !sub.isDeleted));
|
|
66
|
+
business.subunits = filteredSubunits;
|
|
67
|
+
return true;
|
|
68
|
+
}
|
|
69
|
+
return false;
|
|
70
|
+
});
|
|
71
|
+
} else {
|
|
72
|
+
items = showAll ? items : items.slice(0, MAX_INITIAL_ITEMS);
|
|
73
|
+
}
|
|
74
|
+
return items;
|
|
75
|
+
}, [
|
|
76
|
+
filterQuery,
|
|
77
|
+
businesses.list,
|
|
78
|
+
showAll,
|
|
79
|
+
showInactiveBusinesses,
|
|
80
|
+
showSubUnits
|
|
81
|
+
]);
|
|
82
|
+
const hasInactiveItems = businesses.list.some((business)=>business.isDeleted || business.subunits?.some((sub)=>sub.isDeleted));
|
|
83
|
+
const hasItemsWithSubOranizations = businesses.list.some((business)=>business.subunits);
|
|
84
|
+
const getShowAllCount = useCallback(()=>{
|
|
85
|
+
if (showSubUnits && showInactiveBusinesses) {
|
|
86
|
+
return businesses.total;
|
|
87
|
+
}
|
|
88
|
+
if (showSubUnits) {
|
|
89
|
+
return businesses.list.filter((item)=>!item.isDeleted).reduce((total, curr)=>{
|
|
90
|
+
const subUnitsCount = curr.subunits?.filter((sub)=>!sub.isDeleted).length ?? 0;
|
|
91
|
+
return total + 1 + subUnitsCount;
|
|
92
|
+
}, 0);
|
|
93
|
+
}
|
|
94
|
+
if (showInactiveBusinesses) {
|
|
95
|
+
return businesses.list.length;
|
|
96
|
+
}
|
|
97
|
+
return businesses.list.filter((item)=>!item.isDeleted).length;
|
|
98
|
+
}, [
|
|
99
|
+
businesses.list,
|
|
100
|
+
businesses.total,
|
|
101
|
+
showInactiveBusinesses,
|
|
102
|
+
showSubUnits
|
|
103
|
+
]);
|
|
104
|
+
const displayShowAllButton = !showAll && !filterQuery && businesses.list?.length > MAX_INITIAL_ITEMS;
|
|
105
|
+
return /*#__PURE__*/ jsxs("div", {
|
|
106
|
+
children: [
|
|
107
|
+
/*#__PURE__*/ jsx(Heading, {
|
|
108
|
+
as: 'h2',
|
|
109
|
+
level: 3,
|
|
110
|
+
id: 'businessesHeadingId',
|
|
111
|
+
children: filterQuery ? `${visibleItems.length} ${t('rolepicker.BusinessHits')}` : t('rolepicker.BusinessesHeading')
|
|
112
|
+
}),
|
|
113
|
+
hasInactiveItems || hasItemsWithSubOranizations ? /*#__PURE__*/ jsxs("div", {
|
|
114
|
+
className: styles.checkboxGroup,
|
|
115
|
+
children: [
|
|
116
|
+
hasInactiveItems ? /*#__PURE__*/ jsx(Checkbox, {
|
|
117
|
+
checked: showInactiveBusinesses,
|
|
118
|
+
onChange: (e)=>setShowInactiveBusinesses(e.target.checked),
|
|
119
|
+
children: t('rolepicker.ShowInactiveBusinessesHeader')
|
|
120
|
+
}) : null,
|
|
121
|
+
hasItemsWithSubOranizations ? /*#__PURE__*/ jsx(Checkbox, {
|
|
122
|
+
checked: showSubUnits,
|
|
123
|
+
onChange: (e)=>setShowSubUnits(e.target.checked),
|
|
124
|
+
children: t('rolepicker.ShowSubBusinessesHeading')
|
|
125
|
+
}) : null
|
|
126
|
+
]
|
|
127
|
+
}) : null,
|
|
128
|
+
/*#__PURE__*/ jsx("nav", {
|
|
129
|
+
ref: navRef,
|
|
130
|
+
"aria-labelledby": 'businessesHeadingId',
|
|
131
|
+
children: /*#__PURE__*/ jsx("ul", {
|
|
132
|
+
className: styles.businessList,
|
|
133
|
+
children: visibleItems?.map((item)=>{
|
|
134
|
+
if (showSubUnits && item.subunits) {
|
|
135
|
+
const subUnits = showInactiveBusinesses ? item.subunits : item.subunits.filter((sub)=>!sub.isDeleted);
|
|
136
|
+
return /*#__PURE__*/ jsxs("li", {
|
|
137
|
+
children: [
|
|
138
|
+
/*#__PURE__*/ jsx(RolePickerRow, {
|
|
139
|
+
id: item.organizationNumber,
|
|
140
|
+
title: `${item.name} ${item.unitType} ${item.isDeleted ? `(${t('rolepicker.Deleted')})` : ''}`,
|
|
141
|
+
description: /*#__PURE__*/ jsxs(Fragment, {
|
|
142
|
+
children: [
|
|
143
|
+
t('rolepicker.BusinessDescriptionPrefix'),
|
|
144
|
+
' ',
|
|
145
|
+
item.organizationNumber,
|
|
146
|
+
' ',
|
|
147
|
+
/*#__PURE__*/ jsxs("em", {
|
|
148
|
+
children: [
|
|
149
|
+
'(',
|
|
150
|
+
t('rolepicker.MainBusiness'),
|
|
151
|
+
')'
|
|
152
|
+
]
|
|
153
|
+
})
|
|
154
|
+
]
|
|
155
|
+
}),
|
|
156
|
+
svgPath: item.isDeleted ? BriefcaseOffSVGpath : BriefcaseMultipleSVGpath,
|
|
157
|
+
onClick: ()=>{
|
|
158
|
+
handleEntityClicked(item);
|
|
159
|
+
}
|
|
160
|
+
}),
|
|
161
|
+
/*#__PURE__*/ jsx("ul", {
|
|
162
|
+
className: styles.subUnitsList,
|
|
163
|
+
children: subUnits.map((sub)=>{
|
|
164
|
+
return /*#__PURE__*/ jsx("li", {
|
|
165
|
+
className: styles.subUnit,
|
|
166
|
+
children: /*#__PURE__*/ jsx(RolePickerRow, {
|
|
167
|
+
id: sub.organizationNumber,
|
|
168
|
+
title: `${sub.name} ${sub.unitType} ${sub.isDeleted ? `(${t('rolepicker.Deleted')})` : ''}`,
|
|
169
|
+
titleAs: 'h4',
|
|
170
|
+
description: /*#__PURE__*/ jsxs(Fragment, {
|
|
171
|
+
children: [
|
|
172
|
+
t('rolepicker.BusinessDescriptionPrefix'),
|
|
173
|
+
' ',
|
|
174
|
+
sub.organizationNumber,
|
|
175
|
+
' ',
|
|
176
|
+
/*#__PURE__*/ jsxs("em", {
|
|
177
|
+
children: [
|
|
178
|
+
'(',
|
|
179
|
+
t('rolepicker.SubUnit'),
|
|
180
|
+
')'
|
|
181
|
+
]
|
|
182
|
+
})
|
|
183
|
+
]
|
|
184
|
+
}),
|
|
185
|
+
svgPath: sub.isDeleted ? BriefcaseOffSVGpath : BriefcaseSVGpath,
|
|
186
|
+
onClick: ()=>{
|
|
187
|
+
handleEntityClicked(sub);
|
|
188
|
+
}
|
|
189
|
+
})
|
|
190
|
+
}, sub.organizationNumber);
|
|
191
|
+
})
|
|
192
|
+
})
|
|
193
|
+
]
|
|
194
|
+
}, item.organizationNumber);
|
|
195
|
+
} else {
|
|
196
|
+
const svgPath = item.subunits ? BriefcaseMultipleSVGpath : BriefcaseSVGpath;
|
|
197
|
+
return /*#__PURE__*/ jsx("li", {
|
|
198
|
+
children: /*#__PURE__*/ jsx(RolePickerRow, {
|
|
199
|
+
id: item.organizationNumber,
|
|
200
|
+
title: `${item.name} ${item.unitType} ${item.isDeleted ? `(${t('rolepicker.Deleted')})` : ''}`,
|
|
201
|
+
description: `${t('rolepicker.BusinessDescriptionPrefix')} ${item.organizationNumber}`,
|
|
202
|
+
svgPath: item.isDeleted ? BriefcaseOffSVGpath : svgPath,
|
|
203
|
+
onClick: ()=>{
|
|
204
|
+
handleEntityClicked(item);
|
|
205
|
+
}
|
|
206
|
+
})
|
|
207
|
+
}, item.organizationNumber);
|
|
208
|
+
}
|
|
209
|
+
})
|
|
210
|
+
})
|
|
211
|
+
}),
|
|
212
|
+
displayShowAllButton ? /*#__PURE__*/ jsx("div", {
|
|
213
|
+
className: styles.showAllButtonWrapper,
|
|
214
|
+
children: /*#__PURE__*/ jsx(Button, {
|
|
215
|
+
variant: 'tertiary',
|
|
216
|
+
onClick: handleShowAll,
|
|
217
|
+
children: `${t('rolepicker.ShowAll')} ${t('rolepicker.Businesses')} (${getShowAllCount()})`
|
|
218
|
+
})
|
|
219
|
+
}) : null
|
|
220
|
+
]
|
|
221
|
+
});
|
|
222
|
+
};
|
|
223
|
+
RolePickerBusinessList.displayName = 'RolePickerBusinessList';
|
|
224
|
+
|
|
225
|
+
export { RolePickerBusinessList };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
.RolePickerBusinessList-module_businessList__15fne{display:flex;flex-direction:column;gap:var(--spacing-s);list-style-type:none;padding:0}.RolePickerBusinessList-module_checkboxGroup__cdE2w{display:flex;flex-direction:column;gap:var(--spacing-s);margin:var(--spacing-s) 0}@media (min-width:480px){.RolePickerBusinessList-module_checkboxGroup__cdE2w{flex-direction:row}}.RolePickerBusinessList-module_showAllButtonWrapper__ZffHt{margin-top:var(--spacing-xs);text-align:right}.RolePickerBusinessList-module_subUnitsList__bDv87{display:flex;flex-direction:column;gap:var(--spacing-s);list-style-type:none;margin-top:var(--spacing-s);padding:0}.RolePickerBusinessList-module_subUnit__DIX6O{padding-left:var(--spacing-xl)}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./src/RolePickerContext/RolePickerContext";
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./src/RolePickerFilterInput/RolePickerFilterInput";
|
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
import { jsx, jsxs } from 'react/jsx-runtime';
|
|
2
|
+
import { forwardRef, useRef, useState, useEffect } from 'react';
|
|
3
|
+
import { useTranslation } from 'react-i18next';
|
|
4
|
+
import { IconButton } from '@skatteetaten/ds-buttons';
|
|
5
|
+
import { dsI18n } from '@skatteetaten/ds-core-utils';
|
|
6
|
+
import { CancelSVGpath, Icon, FilterSVGpath } from '@skatteetaten/ds-icons';
|
|
7
|
+
import './styles.css';
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
var styles = {
|
|
11
|
+
"searchContainer": "RolePickerFilterInput-module_searchContainer__o-Vzy",
|
|
12
|
+
"topContainer": "RolePickerFilterInput-module_topContainer__yFxDA",
|
|
13
|
+
"label": "RolePickerFilterInput-module_label__lgvnq",
|
|
14
|
+
"clearButton": "RolePickerFilterInput-module_clearButton__etHYm",
|
|
15
|
+
"filterIcon": "RolePickerFilterInput-module_filterIcon__v--p8",
|
|
16
|
+
"inputWrapper": "RolePickerFilterInput-module_inputWrapper__wGC-J",
|
|
17
|
+
"input": "RolePickerFilterInput-module_input__eShOX",
|
|
18
|
+
"srOnly": "RolePickerFilterInput-module_srOnly__CFhaY"
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
const RolePickerFilterInput = /*#__PURE__*/ forwardRef(({ label, value, onChange, onClear }, ref)=>{
|
|
22
|
+
const { t: formsT } = useTranslation('ds_forms', {
|
|
23
|
+
i18n: dsI18n
|
|
24
|
+
});
|
|
25
|
+
const { t } = useTranslation('ds_overlays', {
|
|
26
|
+
i18n: dsI18n
|
|
27
|
+
});
|
|
28
|
+
const inputRef = useRef(null);
|
|
29
|
+
const [liveRegionContent, setLiveRegionContent] = useState('');
|
|
30
|
+
const [showClearButton, setShowClearButton] = useState(!!value);
|
|
31
|
+
useEffect(()=>{
|
|
32
|
+
// Midlertidig tøm innholdet for å tvinge ny kunngjøring
|
|
33
|
+
setLiveRegionContent('');
|
|
34
|
+
const timeoutId = setTimeout(()=>{
|
|
35
|
+
setLiveRegionContent(t('rolepicker.SearchResultUpdated'));
|
|
36
|
+
}, 100); // Kort forsinkelse for å sikre at skjermleseren oppdager endringen
|
|
37
|
+
return ()=>clearTimeout(timeoutId);
|
|
38
|
+
}, [
|
|
39
|
+
value,
|
|
40
|
+
t
|
|
41
|
+
]);
|
|
42
|
+
return /*#__PURE__*/ jsx("div", {
|
|
43
|
+
className: styles.topContainer,
|
|
44
|
+
children: /*#__PURE__*/ jsxs("div", {
|
|
45
|
+
className: styles.searchContainer,
|
|
46
|
+
children: [
|
|
47
|
+
/*#__PURE__*/ jsx("label", {
|
|
48
|
+
className: styles.label,
|
|
49
|
+
htmlFor: 'filterInputId',
|
|
50
|
+
children: label
|
|
51
|
+
}),
|
|
52
|
+
/*#__PURE__*/ jsx("span", {
|
|
53
|
+
className: styles.srOnly,
|
|
54
|
+
id: 'liveSearchId',
|
|
55
|
+
children: t('rolepicker.SearchResultDescription')
|
|
56
|
+
}),
|
|
57
|
+
/*#__PURE__*/ jsx("span", {
|
|
58
|
+
className: styles.srOnly,
|
|
59
|
+
"aria-live": 'assertive',
|
|
60
|
+
"aria-atomic": 'true',
|
|
61
|
+
children: value ? /*#__PURE__*/ jsx("span", {
|
|
62
|
+
children: liveRegionContent
|
|
63
|
+
}) : null
|
|
64
|
+
}),
|
|
65
|
+
/*#__PURE__*/ jsxs("div", {
|
|
66
|
+
className: styles.inputWrapper,
|
|
67
|
+
children: [
|
|
68
|
+
/*#__PURE__*/ jsx("input", {
|
|
69
|
+
ref: inputRef,
|
|
70
|
+
id: 'filterInputId',
|
|
71
|
+
"aria-describedby": 'liveSearchId',
|
|
72
|
+
className: styles.input,
|
|
73
|
+
name: 'filter',
|
|
74
|
+
value: value,
|
|
75
|
+
type: 'search',
|
|
76
|
+
onChange: (event)=>{
|
|
77
|
+
onChange?.(event);
|
|
78
|
+
if (event.target.value.length) {
|
|
79
|
+
setShowClearButton(true);
|
|
80
|
+
} else {
|
|
81
|
+
setShowClearButton(false);
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
}),
|
|
85
|
+
showClearButton && /*#__PURE__*/ jsx(IconButton, {
|
|
86
|
+
type: 'reset',
|
|
87
|
+
className: styles.clearButton,
|
|
88
|
+
size: 'extraSmall',
|
|
89
|
+
svgPath: CancelSVGpath,
|
|
90
|
+
title: formsT('searchfield.ClearButtonTitle'),
|
|
91
|
+
onClick: (event)=>{
|
|
92
|
+
onClear?.(event);
|
|
93
|
+
setShowClearButton(false);
|
|
94
|
+
inputRef.current?.focus();
|
|
95
|
+
}
|
|
96
|
+
}),
|
|
97
|
+
/*#__PURE__*/ jsx(Icon, {
|
|
98
|
+
svgPath: FilterSVGpath,
|
|
99
|
+
className: styles.filterIcon
|
|
100
|
+
})
|
|
101
|
+
]
|
|
102
|
+
})
|
|
103
|
+
]
|
|
104
|
+
})
|
|
105
|
+
});
|
|
106
|
+
});
|
|
107
|
+
RolePickerFilterInput.displayName = 'RolePickerFilterInput';
|
|
108
|
+
|
|
109
|
+
export { RolePickerFilterInput };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
html:has(dialog[open]){overflow:hidden}.RolePickerFilterInput-module_searchContainer__o-Vzy{display:flex;flex-direction:column;gap:var(--spacing-s);position:relative}.RolePickerFilterInput-module_topContainer__yFxDA{--input-padding:var(--spacing-xs) calc(var(--spacing-m)*2 + var(--size-medium) + 2px) var(--spacing-xs) var(--spacing-s)}.RolePickerFilterInput-module_label__lgvnq{color:var(--palette-graphite-100);font-size:var(--font-size-m);font-weight:var(--font-weight-regular);line-height:var(--semantic-line-height-input);overflow-wrap:anywhere}.RolePickerFilterInput-module_clearButton__etHYm{position:absolute;right:var(--spacing-xl);top:5px;z-index:10}.RolePickerFilterInput-module_filterIcon__v--p8{fill:var(--palette-graphite-50);position:absolute;right:var(--spacing-s);top:5px;z-index:10}.RolePickerFilterInput-module_inputWrapper__wGC-J{flex-grow:1;position:relative}.RolePickerFilterInput-module_input__eShOX{-webkit-appearance:none;-moz-appearance:none;appearance:none;background:var(--semantic-page-background);border:none;border-radius:0;box-shadow:inset 0 0 0 1px var(--palette-graphite-100);color:var(--semantic-page-foreground);font-size:var(--font-size-m);line-height:var(--semantic-line-height-input);outline:none;outline-offset:0;padding:var(--input-padding);position:relative;width:100%}.RolePickerFilterInput-module_input__eShOX::-webkit-search-cancel-button{-webkit-appearance:none;appearance:none}.RolePickerFilterInput-module_input__eShOX::-moz-placeholder{color:var(--palette-graphite-50)}.RolePickerFilterInput-module_input__eShOX::placeholder{color:var(--palette-graphite-50)}.RolePickerFilterInput-module_input__eShOX:hover{box-shadow:inset 0 0 0 2px var(--semantic-interactive-main);outline:2px solid var(--semantic-interactive-background);z-index:1}.RolePickerFilterInput-module_input__eShOX:enabled:active,.RolePickerFilterInput-module_input__eShOX:enabled:focus,.RolePickerFilterInput-module_input__eShOX:has(~div :focus-within){box-shadow:inset 0 0 0 2px var(--semantic-interactive-main);outline:1px solid var(--semantic-interactive-main);z-index:1}.RolePickerFilterInput-module_input__eShOX:enabled:active::-moz-selection,.RolePickerFilterInput-module_input__eShOX:enabled:focus::-moz-selection,.RolePickerFilterInput-module_input__eShOX:has(~div :focus-within)::-moz-selection{background:var(--semantic-interactive-background)}.RolePickerFilterInput-module_input__eShOX:enabled:active::selection,.RolePickerFilterInput-module_input__eShOX:enabled:focus::selection,.RolePickerFilterInput-module_input__eShOX:has(~div :focus-within)::selection{background:var(--semantic-interactive-background)}.RolePickerFilterInput-module_srOnly__CFhaY{clip:rect(0,0,0,0);border:0;height:1px;margin:-1px;overflow:hidden;padding:0;position:absolute;white-space:nowrap;width:1px}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./src/RolePickerPeopleList/RolePickerPeopleList";
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
2
|
+
import { useState, useContext, useRef, useMemo } from 'react';
|
|
3
|
+
import { useTranslation } from 'react-i18next';
|
|
4
|
+
import { Button } from '@skatteetaten/ds-buttons';
|
|
5
|
+
import { dsI18n } from '@skatteetaten/ds-core-utils';
|
|
6
|
+
import { PersonSVGpath } from '@skatteetaten/ds-icons';
|
|
7
|
+
import { Heading } from '@skatteetaten/ds-typography';
|
|
8
|
+
import { RolePickerContext } from '../RolePickerContext/index.esm.js';
|
|
9
|
+
import { RolePickerRow } from '../RolePickerRow/index.esm.js';
|
|
10
|
+
import '@skatteetaten/ds-navigation';
|
|
11
|
+
import '@skatteetaten/ds-status';
|
|
12
|
+
import './styles.css';
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
var styles = {
|
|
16
|
+
"peopleList": "RolePickerPeopleList-module_peopleList__dEumR",
|
|
17
|
+
"showAllButtonWrapper": "RolePickerPeopleList-module_showAllButtonWrapper__-ErxO"
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
const MAX_INIITAL_ITEMS = 5;
|
|
21
|
+
const RolePickerPeopleList = ({ people, filterQuery })=>{
|
|
22
|
+
const { t } = useTranslation('ds_overlays', {
|
|
23
|
+
i18n: dsI18n
|
|
24
|
+
});
|
|
25
|
+
const [showAll, setShowAll] = useState(false);
|
|
26
|
+
const ctx = useContext(RolePickerContext);
|
|
27
|
+
const navRef = useRef(null);
|
|
28
|
+
const handleShowAll = ()=>{
|
|
29
|
+
setShowAll(true);
|
|
30
|
+
navRef.current?.querySelectorAll('a')[MAX_INIITAL_ITEMS - 1].focus();
|
|
31
|
+
};
|
|
32
|
+
const handleEntityClicked = async (entity)=>{
|
|
33
|
+
ctx?.setLoadingEntityId(entity.personId);
|
|
34
|
+
ctx?.onEntitySelect?.(entity).then((res)=>{
|
|
35
|
+
if (res?.error) {
|
|
36
|
+
ctx?.setError({
|
|
37
|
+
entityId: entity.personId,
|
|
38
|
+
message: res.error
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
ctx.setLoadingEntityId(undefined);
|
|
42
|
+
});
|
|
43
|
+
};
|
|
44
|
+
const visibleItems = useMemo(()=>{
|
|
45
|
+
if (filterQuery) {
|
|
46
|
+
return people.list.filter((f)=>f.name.toLowerCase().includes(filterQuery.toLowerCase()) || f.personId.includes(filterQuery.toLowerCase()));
|
|
47
|
+
}
|
|
48
|
+
if (showAll) {
|
|
49
|
+
return people.list;
|
|
50
|
+
}
|
|
51
|
+
return people.list.slice(0, MAX_INIITAL_ITEMS);
|
|
52
|
+
}, [
|
|
53
|
+
filterQuery,
|
|
54
|
+
showAll,
|
|
55
|
+
people.list
|
|
56
|
+
]);
|
|
57
|
+
const displayShowAllButton = !showAll && !filterQuery && people.total > MAX_INIITAL_ITEMS;
|
|
58
|
+
return /*#__PURE__*/ jsxs("div", {
|
|
59
|
+
children: [
|
|
60
|
+
/*#__PURE__*/ jsx(Heading, {
|
|
61
|
+
as: 'h2',
|
|
62
|
+
level: 3,
|
|
63
|
+
id: 'otherPeopleHeadingId',
|
|
64
|
+
children: filterQuery ? `${visibleItems.length} ${t('rolepicker.PeopleHits')}` : t('rolepicker.PeopleHeading')
|
|
65
|
+
}),
|
|
66
|
+
/*#__PURE__*/ jsx("nav", {
|
|
67
|
+
ref: navRef,
|
|
68
|
+
"aria-labelledby": 'otherPeopleHeadingId',
|
|
69
|
+
children: /*#__PURE__*/ jsx("ul", {
|
|
70
|
+
className: styles.peopleList,
|
|
71
|
+
children: visibleItems.map((item)=>{
|
|
72
|
+
return /*#__PURE__*/ jsx("li", {
|
|
73
|
+
children: /*#__PURE__*/ jsx(RolePickerRow, {
|
|
74
|
+
id: item.personId,
|
|
75
|
+
title: item.name,
|
|
76
|
+
description: `${t('rolepicker.PeopleDescriptionPrefix')} ${item.personId}`,
|
|
77
|
+
svgPath: PersonSVGpath,
|
|
78
|
+
onClick: ()=>handleEntityClicked(item)
|
|
79
|
+
})
|
|
80
|
+
}, item.personId);
|
|
81
|
+
})
|
|
82
|
+
})
|
|
83
|
+
}),
|
|
84
|
+
displayShowAllButton ? /*#__PURE__*/ jsx("div", {
|
|
85
|
+
className: styles.showAllButtonWrapper,
|
|
86
|
+
children: /*#__PURE__*/ jsx(Button, {
|
|
87
|
+
variant: 'tertiary',
|
|
88
|
+
onClick: handleShowAll,
|
|
89
|
+
children: `${t('rolepicker.ShowAll')} ${t('rolepicker.People')} (${people.total})`
|
|
90
|
+
})
|
|
91
|
+
}) : null
|
|
92
|
+
]
|
|
93
|
+
});
|
|
94
|
+
};
|
|
95
|
+
|
|
96
|
+
export { RolePickerPeopleList };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
.RolePickerPeopleList-module_peopleList__dEumR{display:flex;flex-direction:column;gap:var(--spacing-s);list-style-type:none;padding:0}.RolePickerPeopleList-module_showAllButtonWrapper__-ErxO{margin-top:var(--spacing-xs);text-align:right}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from "./src/RolePickerRow/RolePickerRow";
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
2
|
+
import { useContext } from 'react';
|
|
3
|
+
import { NavigationTile } from '@skatteetaten/ds-navigation';
|
|
4
|
+
import { Alert } from '@skatteetaten/ds-status';
|
|
5
|
+
import { RolePickerContext } from '../RolePickerContext/index.esm.js';
|
|
6
|
+
import './styles.css';
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
var styles = {
|
|
10
|
+
"withAlert": "RolePickerRow-module_withAlert__DxPmf"
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
function RolePickerRow({ id, title, description, svgPath, titleAs, onClick }) {
|
|
14
|
+
const ctx = useContext(RolePickerContext);
|
|
15
|
+
const hasError = ctx?.error?.entityId === id;
|
|
16
|
+
return /*#__PURE__*/ jsxs("div", {
|
|
17
|
+
children: [
|
|
18
|
+
/*#__PURE__*/ jsx(NavigationTile, {
|
|
19
|
+
href: '#',
|
|
20
|
+
className: `${hasError ? styles.withAlert : ''}`,
|
|
21
|
+
titleAs: titleAs ?? 'h3',
|
|
22
|
+
title: title,
|
|
23
|
+
svgPath: svgPath,
|
|
24
|
+
hasSpinner: ctx?.loadingEntityId === id,
|
|
25
|
+
size: 'medium',
|
|
26
|
+
description: description,
|
|
27
|
+
onClick: async (e)=>{
|
|
28
|
+
e.preventDefault();
|
|
29
|
+
onClick?.(e);
|
|
30
|
+
}
|
|
31
|
+
}),
|
|
32
|
+
/*#__PURE__*/ jsx(Alert, {
|
|
33
|
+
variant: 'neutral',
|
|
34
|
+
showAlert: hasError,
|
|
35
|
+
onClose: ()=>ctx?.setError(undefined),
|
|
36
|
+
children: ctx?.error?.message
|
|
37
|
+
})
|
|
38
|
+
]
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
RolePickerRow.displayName = 'RolePickerRow';
|
|
42
|
+
|
|
43
|
+
export { RolePickerRow };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
.RolePickerRow-module_withAlert__DxPmf{box-shadow:none}
|
package/index.esm.js
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
export { Modal, getModalDismissOnEscDefault, getModalDismissOnOutsideClickDefault, getModalPaddingDefault, getModalVariantDefault } from './Modal/index.esm.js';
|
|
2
2
|
export { Popover } from './Popover/index.esm.js';
|
|
3
3
|
import { colorNamesArr } from '@skatteetaten/ds-core-utils';
|
|
4
|
+
export { RolePicker, getRolePickerHideCloseButtonDefault, getRolePickerShowInactiveBusinessesDefault, getRolePickerShowSubunitsDefault } from './RolePicker/index.esm.js';
|
|
4
5
|
export { g as getPopoverColorDefault, a as getPopoverPositionDefault, b as getPopoverRestoreFocusDefault } from './PopoverContent.esm.js';
|
|
5
6
|
import 'react/jsx-runtime';
|
|
6
7
|
import 'react';
|
|
@@ -11,6 +12,14 @@ import '@skatteetaten/ds-typography';
|
|
|
11
12
|
import '@floating-ui/react';
|
|
12
13
|
import './PopoverContext/index.esm.js';
|
|
13
14
|
import './PopoverTrigger/index.esm.js';
|
|
15
|
+
import './RolePickerBusinessList/index.esm.js';
|
|
16
|
+
import '@skatteetaten/ds-forms';
|
|
17
|
+
import './RolePickerContext/index.esm.js';
|
|
18
|
+
import './RolePickerRow/index.esm.js';
|
|
19
|
+
import '@skatteetaten/ds-navigation';
|
|
20
|
+
import '@skatteetaten/ds-status';
|
|
21
|
+
import './RolePickerFilterInput/index.esm.js';
|
|
22
|
+
import './RolePickerPeopleList/index.esm.js';
|
|
14
23
|
|
|
15
24
|
const modalPaddingArr = [
|
|
16
25
|
'none',
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@skatteetaten/ds-overlays",
|
|
3
3
|
"groupId": "no.skatteetaten.aurora",
|
|
4
|
-
"version": "1.
|
|
4
|
+
"version": "1.5.1",
|
|
5
5
|
"main": "./index.esm.js",
|
|
6
6
|
"type": "module",
|
|
7
7
|
"module": "./index.esm.js",
|
|
@@ -16,12 +16,16 @@
|
|
|
16
16
|
"i18next": "^23",
|
|
17
17
|
"react": "^18",
|
|
18
18
|
"react-i18next": "^14",
|
|
19
|
-
"@skatteetaten/ds-core-utils": "1.
|
|
20
|
-
"@skatteetaten/ds-buttons": "1.
|
|
21
|
-
"@skatteetaten/ds-
|
|
22
|
-
"@skatteetaten/ds-
|
|
23
|
-
"@skatteetaten/ds-
|
|
24
|
-
"@
|
|
19
|
+
"@skatteetaten/ds-core-utils": "1.5.1",
|
|
20
|
+
"@skatteetaten/ds-buttons": "1.5.1",
|
|
21
|
+
"@skatteetaten/ds-forms": "1.5.1",
|
|
22
|
+
"@skatteetaten/ds-icons": "1.5.1",
|
|
23
|
+
"@skatteetaten/ds-navigation": "1.5.1",
|
|
24
|
+
"@skatteetaten/ds-typography": "1.5.1",
|
|
25
|
+
"@skatteetaten/ds-progress": "1.5.1",
|
|
26
|
+
"@skatteetaten/ds-status": "1.5.1",
|
|
27
|
+
"@floating-ui/react": "0.26.28",
|
|
28
|
+
"date-fns": "^3"
|
|
25
29
|
},
|
|
26
30
|
"dependencies": {},
|
|
27
31
|
"scripts": {}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
|
-
import { ReactNode } from 'react';
|
|
1
|
+
import { ReactElement, ReactNode } from 'react';
|
|
2
2
|
import { BaseProps } from '@skatteetaten/ds-core-utils';
|
|
3
|
+
import { IconProps } from '@skatteetaten/ds-icons';
|
|
3
4
|
export declare const modalPaddingArr: readonly ["none", "s", "m", "l", "mega"];
|
|
4
5
|
export type ModalPadding = (typeof modalPaddingArr)[number];
|
|
5
6
|
export declare const modalVariantArr: readonly ["outline", "plain", "important"];
|
|
@@ -29,6 +30,12 @@ export interface ModalProps extends BaseProps {
|
|
|
29
30
|
imageSource?: string;
|
|
30
31
|
/** Alt tekst til illustrasjonsbilde. Hvis bildet er meningsbærende, legg på alt tekst. */
|
|
31
32
|
imageSourceAltText?: string;
|
|
33
|
+
/** Icon-komponent som en funksjon som vises over overskriften */
|
|
34
|
+
renderIcon?: () => ReactElement<IconProps>;
|
|
35
|
+
/**
|
|
36
|
+
* Modal i shadowndom.
|
|
37
|
+
* Deprecated: Prop skal fjernes ved lansering av neste major versjon.
|
|
38
|
+
*/
|
|
32
39
|
shadowRootNode?: Document | ShadowRoot;
|
|
33
40
|
/** Callback når modalen lukkes */
|
|
34
41
|
onClose?: () => void;
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import { getRolePickerHideCloseButtonDefault, getRolePickerShowInactiveBusinessesDefault, getRolePickerShowSubunitsDefault } from './defaults';
|
|
2
|
+
import { RolePickerProps } from './RolePicker.types';
|
|
3
|
+
export declare const RolePicker: import("react").ForwardRefExoticComponent<RolePickerProps & import("react").RefAttributes<HTMLDialogElement>>;
|
|
4
|
+
export { getRolePickerHideCloseButtonDefault, getRolePickerShowInactiveBusinessesDefault, getRolePickerShowSubunitsDefault, };
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
import { BaseProps } from '@skatteetaten/ds-core-utils';
|
|
3
|
+
import { ModalProps } from '../Modal/Modal.types';
|
|
4
|
+
export type Paginated<T> = {
|
|
5
|
+
total: number;
|
|
6
|
+
list: T[];
|
|
7
|
+
};
|
|
8
|
+
export type Entity = {
|
|
9
|
+
name: string;
|
|
10
|
+
isDeleted?: boolean;
|
|
11
|
+
type: string;
|
|
12
|
+
};
|
|
13
|
+
export interface Person extends Entity {
|
|
14
|
+
personId: string;
|
|
15
|
+
}
|
|
16
|
+
export interface Business extends Entity {
|
|
17
|
+
organizationNumber: string;
|
|
18
|
+
unitType: string;
|
|
19
|
+
subunits?: Business[];
|
|
20
|
+
mainOrganizationNumber?: string | null;
|
|
21
|
+
}
|
|
22
|
+
export type OnEntitySelectHandler = (entity: Entity) => Promise<{
|
|
23
|
+
error: string;
|
|
24
|
+
} | void>;
|
|
25
|
+
export interface RolePickerProps extends BaseProps, Partial<Pick<ModalProps, 'dismissOnEsc' | 'dismissOnOutsideClick' | 'hideCloseButton' | 'onClose'>> {
|
|
26
|
+
/** Egendefinert tittel på modal. */
|
|
27
|
+
title?: string;
|
|
28
|
+
/** Den nåværende brukeren representert som et Person-objekt. */
|
|
29
|
+
me?: Person;
|
|
30
|
+
/** En paginert liste over personer. */
|
|
31
|
+
people?: Paginated<Person>;
|
|
32
|
+
/** En paginert liste over virksomheter. */
|
|
33
|
+
businesses?: Paginated<Business>;
|
|
34
|
+
/** Om avviklede virksomheter skal vises. */
|
|
35
|
+
showInactiveBusinesses?: boolean;
|
|
36
|
+
/** Om underenheter av virksomheter skal vises. */
|
|
37
|
+
showSubunits?: boolean;
|
|
38
|
+
/** Tilbakekallingsfunksjon for å håndtere valg av virksomhet/person. */
|
|
39
|
+
onEntitySelect?: OnEntitySelectHandler;
|
|
40
|
+
/** Tilbakekallingsfunksjon for å håndtere utlogging. */
|
|
41
|
+
onLogout?: () => void;
|
|
42
|
+
/** Eventuelt annet innhold som rendres etter listen med roller. */
|
|
43
|
+
children?: ReactNode;
|
|
44
|
+
}
|
|
45
|
+
export type RolePickerContextProps = {
|
|
46
|
+
onEntitySelect?: OnEntitySelectHandler;
|
|
47
|
+
error?: {
|
|
48
|
+
entityId: string;
|
|
49
|
+
message: string;
|
|
50
|
+
};
|
|
51
|
+
setError: (error?: {
|
|
52
|
+
entityId: string;
|
|
53
|
+
message: string;
|
|
54
|
+
}) => void;
|
|
55
|
+
loadingEntityId?: string;
|
|
56
|
+
setLoadingEntityId: (entityId?: string) => void;
|
|
57
|
+
};
|
|
@@ -0,0 +1,5 @@
|
|
|
1
|
+
import { RolePickerBusinessListProps } from './RolePickerBusinessList.types';
|
|
2
|
+
export declare const RolePickerBusinessList: {
|
|
3
|
+
({ businesses, filterQuery, showInactiveBusinesses: externalShowInactiveBusinesses, showSubunits: externalShowSubUnits, }: RolePickerBusinessListProps): JSX.Element | null;
|
|
4
|
+
displayName: string;
|
|
5
|
+
};
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
import { JSX } from 'react';
|
|
2
|
+
import { RolePickerRowProps } from './RolePickerRow.types';
|
|
3
|
+
export declare function RolePickerRow({ id, title, description, svgPath, titleAs, onClick, }: RolePickerRowProps): JSX.Element;
|
|
4
|
+
export declare namespace RolePickerRow {
|
|
5
|
+
var displayName: string;
|
|
6
|
+
}
|