@skyscanner/backpack-web 42.2.0 → 42.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (36) hide show
  1. package/bpk-component-chat-bubble/index.d.ts +4 -0
  2. package/bpk-component-chat-bubble/index.js +21 -0
  3. package/bpk-component-chat-bubble/src/BpkChatBubble.d.ts +3 -0
  4. package/bpk-component-chat-bubble/src/BpkChatBubble.js +107 -0
  5. package/bpk-component-chat-bubble/src/BpkChatBubble.module.css +18 -0
  6. package/bpk-component-chat-bubble/src/common-types.d.ts +55 -0
  7. package/bpk-component-chat-bubble/src/common-types.js +29 -0
  8. package/bpk-component-floating-notification/index.d.ts +2 -1
  9. package/bpk-component-floating-notification/index.js +2 -1
  10. package/bpk-component-floating-notification/src/BpkFloatingNotification.d.ts +5 -0
  11. package/bpk-component-floating-notification/src/BpkFloatingNotification.js +8 -2
  12. package/bpk-component-floating-notification/src/BpkFloatingNotification.module.css +1 -1
  13. package/bpk-component-info-banner/src/BpkInfoBanner.module.css +1 -1
  14. package/bpk-component-info-banner/src/BpkInfoBannerInner.js +8 -3
  15. package/bpk-component-info-banner/src/common-types.d.ts +1 -0
  16. package/bpk-component-info-banner/src/common-types.js +2 -1
  17. package/bpk-component-modal/index.d.ts +2 -1
  18. package/bpk-component-modal/index.js +2 -1
  19. package/bpk-component-modal/src/BpkModalV3/{BpkModalV3Body.module.css → BpkModalV3Body/BpkModalV3Body.module.css} +1 -1
  20. package/bpk-component-modal/src/BpkModalV3/BpkModalV3Content/BpkModalV3Content.module.css +18 -0
  21. package/bpk-component-modal/src/BpkModalV3/BpkModalV3Root/BpkModalV3Root.d.ts +2 -2
  22. package/bpk-component-modal/src/BpkModalV3/BpkModalV3Root/BpkModalV3Root.js +39 -16
  23. package/bpk-component-modal/src/BpkModalV3/BpkModalV3Root/useBodyLock.d.ts +9 -0
  24. package/bpk-component-modal/src/BpkModalV3/BpkModalV3Root/useBodyLock.js +69 -0
  25. package/bpk-component-modal/src/BpkModalV3/BpkModalV3Scrim/BpkModalV3Scrim.js +1 -1
  26. package/bpk-component-modal/src/BpkModalV3/{BpkModalV3Scrim.module.css → BpkModalV3Scrim/BpkModalV3Scrim.module.css} +1 -1
  27. package/bpk-component-modal/src/BpkModalV3/common-types.d.ts +7 -1
  28. package/bpk-component-modal/src/BpkModalV3/common-types.js +24 -1
  29. package/package.json +1 -1
  30. package/bpk-component-modal/src/BpkModalV3/BpkModalV3Content.module.css +0 -18
  31. /package/bpk-component-chatbot-input/src/{InputField.module.css → InputField/InputField.module.css} +0 -0
  32. /package/bpk-component-chatbot-input/src/{TextAreaField.module.css → TextAreaField/TextAreaField.module.css} +0 -0
  33. /package/bpk-component-modal/src/BpkModalV3/{BpkModalV3CloseTrigger.module.css → BpkModalV3CloseTrigger/BpkModalV3CloseTrigger.module.css} +0 -0
  34. /package/bpk-component-modal/src/BpkModalV3/{BpkModalV3Header.module.css → BpkModalV3Header/BpkModalV3Header.module.css} +0 -0
  35. /package/bpk-component-modal/src/BpkModalV3/{BpkModalV3HeroImage.module.css → BpkModalV3HeroImage/BpkModalV3HeroImage.module.css} +0 -0
  36. /package/bpk-component-modal/src/BpkModalV3/{BpkModalV3Title.module.css → BpkModalV3Title/BpkModalV3Title.module.css} +0 -0
@@ -0,0 +1,4 @@
1
+ import BpkChatBubble from './src/BpkChatBubble';
2
+ export { CHAT_BUBBLE_TYPE, CHAT_BUBBLE_POSITION } from './src/common-types';
3
+ export type { BpkChatBubbleProps, ChatBubbleType, BubblePosition } from './src/common-types';
4
+ export default BpkChatBubble;
@@ -0,0 +1,21 @@
1
+ /*
2
+ * Backpack - Skyscanner's Design System
3
+ *
4
+ * Copyright 2016 Skyscanner Ltd
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+
19
+ import BpkChatBubble from "./src/BpkChatBubble";
20
+ export { CHAT_BUBBLE_TYPE, CHAT_BUBBLE_POSITION } from "./src/common-types";
21
+ export default BpkChatBubble;
@@ -0,0 +1,3 @@
1
+ import type { BpkChatBubbleProps } from './common-types';
2
+ declare const BpkChatBubble: (props: BpkChatBubbleProps) => import("react/jsx-runtime").JSX.Element;
3
+ export default BpkChatBubble;
@@ -0,0 +1,107 @@
1
+ /*
2
+ * Backpack - Skyscanner's Design System
3
+ *
4
+ * Copyright 2016 Skyscanner Ltd
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+
19
+ import BpkButton, { BUTTON_TYPES, SIZE_TYPES } from "../../bpk-component-button";
20
+ import RedoSmIcon from "../../bpk-component-icon/sm/redo";
21
+ import BpkText, { TEXT_STYLES } from "../../bpk-component-text";
22
+ import BpkThumbButton from "../../bpk-component-thumb-button";
23
+ import { cssModules, getDataComponentAttribute } from "../../bpk-react-utils";
24
+ import { CHAT_BUBBLE_TYPE } from "./common-types";
25
+ import STYLES from "./BpkChatBubble.module.css";
26
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
27
+ const getClassName = cssModules(STYLES);
28
+ const clampAndSnap = (ms, maxDelay = 300) => {
29
+ const v = Math.min(ms, maxDelay);
30
+ return Math.round(v / 50) * 50;
31
+ };
32
+ const BpkChatBubble = props => {
33
+ const {
34
+ animationDelay = 0,
35
+ children,
36
+ type
37
+ } = props;
38
+ const userPosition = 'userPosition' in props ? props.userPosition : undefined;
39
+ const systemPosition = 'systemPosition' in props ? props.systemPosition : undefined;
40
+ const showFeedback = 'showFeedback' in props ? props.showFeedback ?? false : false;
41
+ const selectedFeedback = 'selectedFeedback' in props ? props.selectedFeedback ?? null : null;
42
+ const onFeedbackClick = 'onFeedbackClick' in props ? props.onFeedbackClick : undefined;
43
+ const onRetry = 'onRetry' in props ? props.onRetry : undefined;
44
+ const retryDisabled = 'retryDisabled' in props ? props.retryDisabled ?? false : false;
45
+ const retryLabel = 'retryLabel' in props ? props.retryLabel : '';
46
+ const onSuggestionClick = 'onSuggestionClick' in props ? props.onSuggestionClick : undefined;
47
+ const thumbsUpLabel = 'thumbsUpLabel' in props ? props.thumbsUpLabel ?? 'Rate as useful' : 'Rate as useful';
48
+ const thumbsDownLabel = 'thumbsDownLabel' in props ? props.thumbsDownLabel ?? 'Rate as not useful' : 'Rate as not useful';
49
+ const isUser = type === CHAT_BUBBLE_TYPE.user;
50
+ const isSuggestion = type === CHAT_BUBBLE_TYPE.button;
51
+ const isRetry = type === CHAT_BUBBLE_TYPE.retry;
52
+ const isBot = type === CHAT_BUBBLE_TYPE.bot;
53
+ const isSystem = isBot || isRetry;
54
+ const snapped = clampAndSnap(animationDelay);
55
+ const inlineStyle = {
56
+ '--anim-delay': `${snapped}ms`
57
+ };
58
+ const containerClassName = getClassName('bpk-chat-bubble', 'bpk-chat-bubble--animated', isUser && 'bpk-chat-bubble--user', isBot && 'bpk-chat-bubble--bot', isRetry && 'bpk-chat-bubble--retry', isSuggestion && 'bpk-chat-bubble--button', isUser && userPosition === 'first' && 'bpk-chat-bubble--user-first', isUser && userPosition === 'middle' && 'bpk-chat-bubble--user-middle', isUser && userPosition === 'last' && 'bpk-chat-bubble--user-last', isSystem && systemPosition === 'first' && 'bpk-chat-bubble--system-first', isSystem && systemPosition === 'middle' && 'bpk-chat-bubble--system-middle', isSystem && systemPosition === 'last' && 'bpk-chat-bubble--system-last');
59
+ if (isSuggestion) {
60
+ return /*#__PURE__*/_jsx("button", {
61
+ type: "button",
62
+ className: containerClassName,
63
+ style: inlineStyle,
64
+ onClick: onSuggestionClick,
65
+ "data-testid": "bpk-chat-bubble-suggestion",
66
+ ...getDataComponentAttribute('ChatBubble'),
67
+ children: children
68
+ });
69
+ }
70
+ return /*#__PURE__*/_jsxs("div", {
71
+ className: containerClassName,
72
+ style: inlineStyle,
73
+ "data-testid": "bpk-chat-bubble",
74
+ ...getDataComponentAttribute('ChatBubble'),
75
+ children: [/*#__PURE__*/_jsxs("div", {
76
+ className: getClassName('bpk-chat-bubble__content'),
77
+ children: [children, isRetry && onRetry && /*#__PURE__*/_jsx("div", {
78
+ className: getClassName('bpk-chat-bubble__retry'),
79
+ children: /*#__PURE__*/_jsx(BpkButton, {
80
+ type: BUTTON_TYPES.primary,
81
+ size: SIZE_TYPES.small,
82
+ onClick: onRetry,
83
+ disabled: retryDisabled,
84
+ leadingIcon: /*#__PURE__*/_jsx(RedoSmIcon, {}),
85
+ children: /*#__PURE__*/_jsx(BpkText, {
86
+ textStyle: TEXT_STYLES.label1,
87
+ children: retryLabel
88
+ })
89
+ })
90
+ })]
91
+ }), showFeedback && isBot && /*#__PURE__*/_jsxs("div", {
92
+ className: getClassName('bpk-chat-bubble__thumbs'),
93
+ children: [/*#__PURE__*/_jsx(BpkThumbButton, {
94
+ type: "up",
95
+ selected: selectedFeedback === 'up',
96
+ onClick: onFeedbackClick ?? (() => {}),
97
+ accessibilityLabel: thumbsUpLabel
98
+ }), /*#__PURE__*/_jsx(BpkThumbButton, {
99
+ type: "down",
100
+ selected: selectedFeedback === 'down',
101
+ onClick: onFeedbackClick ?? (() => {}),
102
+ accessibilityLabel: thumbsDownLabel
103
+ })]
104
+ })]
105
+ });
106
+ };
107
+ export default BpkChatBubble;
@@ -0,0 +1,18 @@
1
+ /*
2
+ * Backpack - Skyscanner's Design System
3
+ *
4
+ * Copyright 2016 Skyscanner Ltd
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+ @keyframes bpk-chat-bubble-entrance{from{transform:translateY(0.625rem) scale(0.98);opacity:0}to{transform:translateY(0) scale(1);opacity:1}}@keyframes bpk-chat-bubble-entrance-reduced{from{opacity:0}to{opacity:1}}.bpk-chat-bubble{width:fit-content;max-width:17.5rem;padding:1rem;background:#fff;color:#161616;overflow-wrap:break-word;word-wrap:break-word}.bpk-chat-bubble--bot,.bpk-chat-bubble--retry{align-self:flex-start}.bpk-chat-bubble--button,.bpk-chat-bubble--user{align-self:flex-end}.bpk-chat-bubble--button,.bpk-chat-bubble--user,.bpk-chat-bubble--bot,.bpk-chat-bubble--retry{border-radius:1.5rem}html[dir=rtl] .bpk-chat-bubble{direction:rtl}.bpk-chat-bubble--animated{transform:translateY(0.625rem) scale(0.98);opacity:0;animation:bpk-chat-bubble-entrance 200ms cubic-bezier(0.2, 0, 0, 1) forwards;animation-delay:var(--anim-delay, 0ms)}@media(prefers-reduced-motion: reduce){.bpk-chat-bubble--animated{transform:translateY(0) scale(1);animation:bpk-chat-bubble-entrance-reduced 200ms ease-out forwards}}.bpk-chat-bubble--bot,.bpk-chat-bubble--retry{text-align:start}.bpk-chat-bubble--user{background:#0062e3;color:#fff;text-align:start}.bpk-chat-bubble--button{width:fit-content;transition:transform 200ms ease-in-out,box-shadow 200ms ease-in-out;border:1px solid #0062e3;background:rgba(0,0,0,0);color:#0062e3;text-align:start;cursor:pointer;border-end-end-radius:.25rem}.bpk-no-touch-support .bpk-chat-bubble--button:hover:not(:active):not(:disabled){transform:translateY(-0.0625rem);box-shadow:0px 1px 3px 0px rgba(37,32,31,.3)}:global(.bpk-no-touch-support) .bpk-chat-bubble--button:hover:not(:active):not(:disabled){transform:translateY(-0.0625rem);box-shadow:0px 1px 3px 0px rgba(37,32,31,.3)}.bpk-chat-bubble--button:active{transform:translateY(0);box-shadow:none}.bpk-chat-bubble--system-first{border-end-start-radius:.25rem}.bpk-chat-bubble--system-middle{border-start-start-radius:.25rem;border-end-start-radius:.25rem}.bpk-chat-bubble--system-last{border-start-start-radius:.25rem}.bpk-chat-bubble--user-first{border-end-end-radius:.25rem}.bpk-chat-bubble--user-middle{border-start-end-radius:.25rem;border-end-end-radius:.25rem}.bpk-chat-bubble--user-last{border-start-end-radius:.25rem}.bpk-chat-bubble__content p+p{margin-top:1rem}.bpk-chat-bubble__retry{margin-top:1rem}.bpk-chat-bubble__retry button{padding:0 1rem}.bpk-chat-bubble__thumbs{display:flex;margin-top:.5rem;align-items:center;gap:1rem}
@@ -0,0 +1,55 @@
1
+ import type { ReactNode } from 'react';
2
+ import type { ThumbsButtonType } from '../../bpk-component-thumb-button';
3
+ export declare const CHAT_BUBBLE_TYPE: {
4
+ readonly user: "user";
5
+ readonly bot: "bot";
6
+ readonly retry: "retry";
7
+ readonly button: "button";
8
+ };
9
+ export declare const CHAT_BUBBLE_POSITION: {
10
+ readonly first: "first";
11
+ readonly middle: "middle";
12
+ readonly last: "last";
13
+ };
14
+ export type ChatBubbleType = (typeof CHAT_BUBBLE_TYPE)[keyof typeof CHAT_BUBBLE_TYPE];
15
+ export type BubblePosition = (typeof CHAT_BUBBLE_POSITION)[keyof typeof CHAT_BUBBLE_POSITION];
16
+ type BaseBubbleProps = {
17
+ /** Content to render inside the bubble */
18
+ children?: ReactNode;
19
+ /** Animation entrance delay in milliseconds (0–300, snapped to nearest 50ms) */
20
+ animationDelay?: number;
21
+ };
22
+ export type BpkChatBubbleProps = (BaseBubbleProps & {
23
+ type: 'user';
24
+ /** Position within a sequence of user bubbles, affects border-radius */
25
+ userPosition?: BubblePosition;
26
+ }) | (BaseBubbleProps & {
27
+ type: 'bot';
28
+ /** Position within a sequence of same-sender bubbles, affects border-radius */
29
+ systemPosition?: BubblePosition;
30
+ /** Show thumbs up/down feedback buttons */
31
+ showFeedback?: boolean;
32
+ /** Currently selected feedback type */
33
+ selectedFeedback?: ThumbsButtonType | null;
34
+ /** Called when a feedback thumb button is clicked */
35
+ onFeedbackClick?: (type: ThumbsButtonType) => void;
36
+ /** Accessibility label for the thumbs up button (defaults to "Rate as useful") */
37
+ thumbsUpLabel?: string;
38
+ /** Accessibility label for the thumbs down button (defaults to "Rate as not useful") */
39
+ thumbsDownLabel?: string;
40
+ }) | (BaseBubbleProps & {
41
+ type: 'retry';
42
+ /** Position within a sequence of same-sender bubbles, affects border-radius */
43
+ systemPosition?: BubblePosition;
44
+ /** Label for the retry button */
45
+ retryLabel: string;
46
+ /** Called when retry button is clicked */
47
+ onRetry?: () => void;
48
+ /** Whether the retry button is disabled */
49
+ retryDisabled?: boolean;
50
+ }) | (BaseBubbleProps & {
51
+ type: 'button';
52
+ /** Called when the suggestion is clicked */
53
+ onSuggestionClick?: () => void;
54
+ });
55
+ export {};
@@ -0,0 +1,29 @@
1
+ /*
2
+ * Backpack - Skyscanner's Design System
3
+ *
4
+ * Copyright 2016 Skyscanner Ltd
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+
19
+ export const CHAT_BUBBLE_TYPE = {
20
+ user: 'user',
21
+ bot: 'bot',
22
+ retry: 'retry',
23
+ button: 'button'
24
+ };
25
+ export const CHAT_BUBBLE_POSITION = {
26
+ first: 'first',
27
+ middle: 'middle',
28
+ last: 'last'
29
+ };
@@ -1,3 +1,4 @@
1
- import BpkFloatingNotification, { type Props as BpkFloatingNotificationProps } from './src/BpkFloatingNotification';
1
+ import BpkFloatingNotification, { NOTIFICATION_TYPES, type Props as BpkFloatingNotificationProps } from './src/BpkFloatingNotification';
2
2
  export type { BpkFloatingNotificationProps };
3
+ export { NOTIFICATION_TYPES };
3
4
  export default BpkFloatingNotification;
@@ -14,5 +14,6 @@
14
14
  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
15
  * See the License for the specific language governing permissions and
16
16
  * limitations under the License.
17
- */import BpkFloatingNotification from "./src/BpkFloatingNotification";
17
+ */import BpkFloatingNotification, { NOTIFICATION_TYPES } from "./src/BpkFloatingNotification";
18
+ export { NOTIFICATION_TYPES };
18
19
  export default BpkFloatingNotification;
@@ -1,4 +1,8 @@
1
1
  import type { MouseEvent, FunctionComponent } from 'react';
2
+ export declare const NOTIFICATION_TYPES: {
3
+ readonly default: "default";
4
+ readonly critical: "critical";
5
+ };
2
6
  export type Props = {
3
7
  animateOnEnter?: boolean;
4
8
  animateOnExit?: boolean;
@@ -16,6 +20,7 @@ export type Props = {
16
20
  */
17
21
  onExit?: () => void;
18
22
  text: string;
23
+ type?: (typeof NOTIFICATION_TYPES)[keyof typeof NOTIFICATION_TYPES];
19
24
  [rest: string]: any;
20
25
  };
21
26
  declare const BpkFloatingNotification: (props: Props) => import("react/jsx-runtime").JSX.Element;
@@ -18,13 +18,17 @@
18
18
 
19
19
  import { useEffect, useState } from 'react';
20
20
  import { CSSTransition } from 'react-transition-group';
21
- import BpkAriaLive from "../../bpk-component-aria-live";
21
+ import BpkAriaLive, { ARIA_LIVE_POLITENESS_SETTINGS } from "../../bpk-component-aria-live";
22
22
  import BpkButton, { BUTTON_TYPES } from "../../bpk-component-button";
23
23
  import BpkText, { TEXT_STYLES } from "../../bpk-component-text";
24
24
  import { cssModules, getDataComponentAttribute } from "../../bpk-react-utils";
25
25
  import STYLES from "./BpkFloatingNotification.module.css";
26
26
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
27
27
  const getClassName = cssModules(STYLES);
28
+ export const NOTIFICATION_TYPES = {
29
+ default: 'default',
30
+ critical: 'critical'
31
+ };
28
32
  const BpkFloatingNotification = props => {
29
33
  const [showMessage, setShowMessage] = useState(true);
30
34
  const {
@@ -37,9 +41,10 @@ const BpkFloatingNotification = props => {
37
41
  onClick,
38
42
  onExit,
39
43
  text,
44
+ type = NOTIFICATION_TYPES.default,
40
45
  ...rest
41
46
  } = props;
42
- const classNames = getClassName('bpk-floating-notification', className);
47
+ const classNames = getClassName('bpk-floating-notification', type === NOTIFICATION_TYPES.critical && 'bpk-floating-notification--critical', className);
43
48
  useEffect(() => {
44
49
  let timer;
45
50
  if (hideAfter) {
@@ -78,6 +83,7 @@ const BpkFloatingNotification = props => {
78
83
  })
79
84
  }), /*#__PURE__*/_jsx(BpkAriaLive, {
80
85
  "aria-hidden": true,
86
+ politenessSetting: type === NOTIFICATION_TYPES.critical ? ARIA_LIVE_POLITENESS_SETTINGS.assertive : ARIA_LIVE_POLITENESS_SETTINGS.polite,
81
87
  children: text
82
88
  }), ctaText && /*#__PURE__*/_jsx("div", {
83
89
  className: getClassName('bpk-floating-notification__cta'),
@@ -15,4 +15,4 @@
15
15
  * See the License for the specific language governing permissions and
16
16
  * limitations under the License.
17
17
  */
18
- .bpk-floating-notification{position:fixed;right:0;bottom:2rem;left:0;display:flex;z-index:2;max-width:25rem;margin:auto;padding:1.5rem;align-items:center;transition:opacity 400ms ease-in-out,transform 400ms ease-in-out;border-radius:.75rem;background:#05203c;color:#fff;box-shadow:0px 12px 50px 0px rgba(37,32,31,.25),0px 4px 14px 0px rgba(37,32,31,.25)}@media(max-width: 32rem){.bpk-floating-notification{max-width:100%;padding:1rem}}.bpk-floating-notification--leave{transform:translateY(0);opacity:1}.bpk-floating-notification--leave-active{transform:translateY(2rem);opacity:0}.bpk-floating-notification--leave-done{opacity:0}.bpk-floating-notification--appear{transform:translateY(2rem);opacity:0}.bpk-floating-notification--appear-active{transform:translateY(0);opacity:1}.bpk-floating-notification__icon{margin-right:.5rem;margin-left:.25rem;flex-shrink:0;transform:translateY(0.25rem);text-align:bottom;fill:#fff}.bpk-floating-notification__text{margin-inline-end:.5rem}.bpk-floating-notification__cta{margin-inline-start:auto}
18
+ .bpk-floating-notification{position:fixed;right:0;bottom:2rem;left:0;display:flex;z-index:2;max-width:25rem;margin:auto;padding:1.5rem;align-items:center;transition:opacity 400ms ease-in-out,transform 400ms ease-in-out;border-radius:.75rem;background:#05203c;color:#fff;box-shadow:0px 12px 50px 0px rgba(37,32,31,.25),0px 4px 14px 0px rgba(37,32,31,.25)}@media(max-width: 32rem){.bpk-floating-notification{max-width:100%;padding:1rem}}.bpk-floating-notification--critical{background-color:#e70866}.bpk-floating-notification--leave{transform:translateY(0);opacity:1}.bpk-floating-notification--leave-active{transform:translateY(2rem);opacity:0}.bpk-floating-notification--leave-done{opacity:0}.bpk-floating-notification--appear{transform:translateY(2rem);opacity:0}.bpk-floating-notification--appear-active{transform:translateY(0);opacity:1}.bpk-floating-notification__icon{margin-right:.5rem;margin-left:.25rem;flex-shrink:0;transform:translateY(0.25rem);text-align:bottom;fill:#fff}.bpk-floating-notification__text{margin-inline-end:.5rem}.bpk-floating-notification__cta{margin-inline-start:auto}
@@ -15,4 +15,4 @@
15
15
  * See the License for the specific language governing permissions and
16
16
  * limitations under the License.
17
17
  */
18
- .bpk-info-banner{padding:.5rem 1rem;overflow:hidden;border-radius:.5rem;margin:0;font-size:.875rem;line-height:1.25rem;font-weight:400}.bpk-info-banner--style-default{background-color:#eff3f8}.bpk-info-banner--style-onContrast{background-color:#fff}.bpk-info-banner__header{display:flex;flex-direction:row;align-items:flex-start}.bpk-info-banner__header--expandable{width:100%;padding:0;border:none;background-color:rgba(0,0,0,0);text-align:start;cursor:pointer}.bpk-info-banner__icon,.bpk-info-banner__toggle{padding:.125rem 0}.bpk-info-banner__message{padding:.25rem .5rem;flex-grow:1}.bpk-info-banner__success-icon{fill:#0c838a}.bpk-info-banner__warning-icon{fill:#f55d42}.bpk-info-banner__error-icon{fill:#e70866}.bpk-info-banner__info-icon{fill:#626971}.bpk-info-banner__toggle-button{padding:0;border:0;background-color:rgba(0,0,0,0);cursor:pointer;appearance:none;fill:#626971}.bpk-info-banner__children-container{color:#161616;font-size:.875rem;line-height:1.25rem;font-weight:400}.bpk-info-banner__children-container--with-action{padding:.25rem 0 .25rem}.bpk-info-banner__children-container--no-action{padding:.25rem 0 .5rem}
18
+ .bpk-info-banner{padding:.5rem 1rem;overflow:hidden;border-radius:.5rem;margin:0;font-size:.875rem;line-height:1.25rem;font-weight:400}.bpk-info-banner--style-default{background-color:#eff3f8}.bpk-info-banner--style-onContrast{background-color:#fff}.bpk-info-banner__header{display:flex;flex-direction:row;align-items:flex-start}.bpk-info-banner__header--expandable{width:100%;padding:0;border:none;background-color:rgba(0,0,0,0);text-align:start;cursor:pointer}.bpk-info-banner__icon,.bpk-info-banner__toggle{padding:.125rem 0}.bpk-info-banner__message{padding:.25rem .5rem;flex-grow:1}.bpk-info-banner__success-icon{fill:#0c838a}.bpk-info-banner__warning-icon{fill:#f55d42}.bpk-info-banner__error-icon{fill:#e70866}.bpk-info-banner__info-icon{fill:#626971}.bpk-info-banner__critical-icon{fill:#fff}.bpk-info-banner--critical{background-color:#e70866;color:#fff}.bpk-info-banner--critical .bpk-info-banner__message{color:#fff}.bpk-info-banner--critical .bpk-info-banner__toggle-button{fill:#fff}.bpk-info-banner--critical .bpk-info-banner__children-container,.bpk-info-banner--critical .bpk-info-banner__children-container--with-action,.bpk-info-banner--critical .bpk-info-banner__children-container--no-action{color:#fff}.bpk-info-banner__toggle-button{padding:0;border:0;background-color:rgba(0,0,0,0);cursor:pointer;appearance:none;fill:#626971}.bpk-info-banner__children-container{color:#161616;font-size:.875rem;line-height:1.25rem;font-weight:400}.bpk-info-banner__children-container--with-action{padding:.25rem 0 .25rem}.bpk-info-banner__children-container--no-action{padding:.25rem 0 .5rem}
@@ -27,6 +27,7 @@ import BpkCloseButton from "../../bpk-component-close-button";
27
27
  import { withButtonAlignment } from "../../bpk-component-icon";
28
28
  import ChevronDownIcon from "../../bpk-component-icon/sm/chevron-down";
29
29
  import ChevronUpIcon from "../../bpk-component-icon/sm/chevron-up";
30
+ import ExclamationCircleIcon from "../../bpk-component-icon/sm/exclamation-circle";
30
31
  import InfoCircleIcon from "../../bpk-component-icon/sm/information-circle";
31
32
  import TickCircleIcon from "../../bpk-component-icon/sm/tick-circle";
32
33
  import BpkLink from "../../bpk-component-link";
@@ -49,14 +50,16 @@ const getIconForType = (type, CustomIcon) => {
49
50
  [ALERT_TYPES.SUCCESS]: getClassName('bpk-info-banner__success-icon'),
50
51
  [ALERT_TYPES.WARNING]: getClassName('bpk-info-banner__warning-icon'),
51
52
  [ALERT_TYPES.ERROR]: getClassName('bpk-info-banner__error-icon'),
52
- [ALERT_TYPES.INFO]: getClassName('bpk-info-banner__info-icon')
53
+ [ALERT_TYPES.INFO]: getClassName('bpk-info-banner__info-icon'),
54
+ [ALERT_TYPES.CRITICAL]: getClassName('bpk-info-banner__critical-icon')
53
55
  };
54
56
  const className = classMap[type];
55
57
  const componentMap = {
56
58
  [ALERT_TYPES.SUCCESS]: TickCircleIcon,
57
59
  [ALERT_TYPES.WARNING]: InfoCircleIcon,
58
60
  [ALERT_TYPES.ERROR]: InfoCircleIcon,
59
- [ALERT_TYPES.INFO]: InfoCircleIcon
61
+ [ALERT_TYPES.INFO]: InfoCircleIcon,
62
+ [ALERT_TYPES.CRITICAL]: ExclamationCircleIcon
60
63
  };
61
64
  const Icon = CustomIcon || componentMap[type];
62
65
  const AlignedIcon = withButtonAlignment(Icon);
@@ -139,7 +142,8 @@ const BpkInfoBannerInner = ({
139
142
  children: /*#__PURE__*/_jsx(BpkCloseButton, {
140
143
  onClick: onBannerDismiss,
141
144
  "aria-label": dismissButtonLabel,
142
- label: dismissButtonLabel
145
+ label: dismissButtonLabel,
146
+ onDark: type === ALERT_TYPES.CRITICAL
143
147
  })
144
148
  })]
145
149
  }), /*#__PURE__*/_jsxs(BpkAnimateHeight, {
@@ -149,6 +153,7 @@ const BpkInfoBannerInner = ({
149
153
  className: childrenContainerClassName,
150
154
  children: children
151
155
  }), isExpandable && action && /*#__PURE__*/_jsx(BpkLink, {
156
+ alternate: type === ALERT_TYPES.CRITICAL,
152
157
  onClick: action.callback,
153
158
  href: "#",
154
159
  children: action.title
@@ -4,6 +4,7 @@ export declare const ALERT_TYPES: {
4
4
  readonly WARNING: "warning";
5
5
  readonly ERROR: "error";
6
6
  readonly INFO: "info";
7
+ readonly CRITICAL: "critical";
7
8
  };
8
9
  export declare const STYLE_TYPES: {
9
10
  DEFAULT: string;
@@ -20,7 +20,8 @@ export const ALERT_TYPES = {
20
20
  SUCCESS: 'success',
21
21
  WARNING: 'warning',
22
22
  ERROR: 'error',
23
- INFO: 'info'
23
+ INFO: 'info',
24
+ CRITICAL: 'critical'
24
25
  };
25
26
  export const STYLE_TYPES = {
26
27
  DEFAULT: 'default',
@@ -2,9 +2,10 @@ import BpkModal from './src/BpkModal';
2
2
  import { MODAL_STYLING } from './src/BpkModalInner';
3
3
  import { BpkModalV2 } from './src/BpkModalV2/BpkModal';
4
4
  import BpkModalV3 from './src/BpkModalV3/BpkModalV3';
5
+ import { MODAL_V3_TYPES } from './src/BpkModalV3/common-types';
5
6
  import { propTypes, defaultProps } from './src/legacy-prop-types';
6
7
  import themeAttributes from './src/themeAttributes';
7
8
  import type { Props } from './src/BpkModal';
8
9
  export type BpkModalProps = Props;
9
10
  export default BpkModal;
10
- export { propTypes, defaultProps, themeAttributes, BpkModalV2, BpkModalV3, MODAL_STYLING, };
11
+ export { propTypes, defaultProps, themeAttributes, BpkModalV2, BpkModalV3, MODAL_V3_TYPES, MODAL_STYLING, };
@@ -20,8 +20,9 @@ import BpkModal from "./src/BpkModal";
20
20
  import { MODAL_STYLING } from "./src/BpkModalInner";
21
21
  import { BpkModalV2 } from "./src/BpkModalV2/BpkModal";
22
22
  import BpkModalV3 from "./src/BpkModalV3/BpkModalV3";
23
+ import { MODAL_V3_TYPES } from "./src/BpkModalV3/common-types";
23
24
  // @ts-expect-error Untyped import. See `decisions/imports-ts-suppressions.md`.
24
25
  import { propTypes, defaultProps } from "./src/legacy-prop-types";
25
26
  import themeAttributes from "./src/themeAttributes";
26
27
  export default BpkModal;
27
- export { propTypes, defaultProps, themeAttributes, BpkModalV2, BpkModalV3, MODAL_STYLING };
28
+ export { propTypes, defaultProps, themeAttributes, BpkModalV2, BpkModalV3, MODAL_V3_TYPES, MODAL_STYLING };
@@ -15,4 +15,4 @@
15
15
  * See the License for the specific language governing permissions and
16
16
  * limitations under the License.
17
17
  */
18
- .bpk-modal-v3__body{flex:1;overflow-y:auto}
18
+ .bpk-modal-v3__body{flex:1;overflow-y:auto;overscroll-behavior:contain}
@@ -0,0 +1,18 @@
1
+ /*
2
+ * Backpack - Skyscanner's Design System
3
+ *
4
+ * Copyright 2016 Skyscanner Ltd
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+ .bpk-modal-v3__positioner{position:fixed;display:flex;z-index:1100;justify-content:center;align-items:center;inset:0;pointer-events:none}.bpk-modal-v3__positioner--sheet{align-items:flex-end}.bpk-modal-v3__positioner--full{align-items:stretch}.bpk-modal-v3__positioner--chatbot{align-items:stretch}.bpk-modal-v3__content{position:relative;display:flex;flex-direction:column;background-color:#fff;overflow:clip;pointer-events:none}.bpk-modal-v3__content[data-state=open]{pointer-events:auto}.bpk-modal-v3__content--default{width:100%;max-width:50rem;max-height:90vh;transform:scale(0.9);transition:transform 200ms ease-in-out;border-radius:1.5rem;opacity:0;box-shadow:0px 4px 14px 0px rgba(37,32,31,.25)}@media(max-width: 32rem){.bpk-modal-v3__content--default{max-width:none;height:100%;max-height:none;transform:translateY(100%);border-radius:0;box-shadow:none}.bpk-modal-v3__content--default[data-state=open]{transform:translateY(0)}.bpk-modal-v3__content--default[data-state=closed]{transform:translateY(100%)}}.bpk-modal-v3__content--default[data-state=open]{transform:scale(1);opacity:1}.bpk-modal-v3__content--default[data-state=closed]{transform:scale(0.9);opacity:0}.bpk-modal-v3__content--sheet{width:100%;height:fit-content;max-height:100dvh;transform:translateY(100%);transition:opacity 400ms cubic-bezier(0.5, 0, 0, 1),transform 400ms cubic-bezier(0.5, 0, 0, 1);border-radius:1.5rem 1.5rem 0 0;opacity:0;box-shadow:0px 4px 14px 0px rgba(37,32,31,.25)}.bpk-modal-v3__content--sheet[data-state=open]{transform:translateY(0);opacity:1}.bpk-modal-v3__content--sheet[data-state=closed]{transform:translateY(100%);opacity:0}.bpk-modal-v3__content--full{width:100%;height:100%;transform:translateY(100%);transition:opacity 400ms cubic-bezier(0.5, 0, 0, 1),transform 400ms cubic-bezier(0.5, 0, 0, 1);border-radius:0;opacity:0}.bpk-modal-v3__content--full[data-state=open]{transform:translateY(0);opacity:1}.bpk-modal-v3__content--full[data-state=closed]{transform:translateY(100%);opacity:0}.bpk-modal-v3__content--chatbot{width:100%;height:100%;transform:translateX(100%);transition:transform 400ms cubic-bezier(0.5, 0, 0, 1);border-radius:0;background-color:#eff3f8}html[dir=rtl] .bpk-modal-v3__content--chatbot{transform:translateX(-100%)}.bpk-modal-v3__content--chatbot[data-state=open]{transform:translateX(0)}html[dir=rtl] .bpk-modal-v3__content--chatbot[data-state=open]{transform:translateX(0)}.bpk-modal-v3__content--chatbot[data-state=closed]{transform:translateX(100%)}html[dir=rtl] .bpk-modal-v3__content--chatbot[data-state=closed]{transform:translateX(-100%)}@media(prefers-reduced-motion: reduce){.bpk-modal-v3__content--default{transform:scale(1);transition:none;opacity:1}}@media(prefers-reduced-motion: reduce)and (max-width: 32rem){.bpk-modal-v3__content--default{transform:translateY(0)}}@media(prefers-reduced-motion: reduce){.bpk-modal-v3__content--sheet,.bpk-modal-v3__content--full{transform:translateY(0);transition:none;opacity:1}.bpk-modal-v3__content--chatbot{transform:translateX(0);transition:none;opacity:1}html[dir=rtl] .bpk-modal-v3__content--chatbot{transform:translateX(0)}}
@@ -1,5 +1,5 @@
1
- import type { ReactNode } from 'react';
2
- import type { BpkModalV3Type } from '../common-types';
1
+ import { type ReactNode } from 'react';
2
+ import { type BpkModalV3Type } from '../common-types';
3
3
  type BpkModalV3RootProps = {
4
4
  children: ReactNode;
5
5
  open?: boolean;
@@ -16,29 +16,52 @@
16
16
  * limitations under the License.
17
17
  */
18
18
 
19
+ import { useEffect, useState } from 'react';
19
20
  import { Dialog } from '@ark-ui/react';
21
+ import { durationBase } from '@skyscanner/bpk-foundations-web/tokens/base.es6';
20
22
  import { getDataComponentAttribute } from "../../../../bpk-react-utils";
21
23
  import { ModalTypeProvider } from "../BpkModalV3Context";
24
+ import { MODAL_V3_TYPES } from "../common-types";
25
+ import useBodyLock from "./useBodyLock";
22
26
  import { jsx as _jsx } from "react/jsx-runtime";
23
27
  const BpkModalV3Root = ({
24
28
  children,
25
29
  onOpenChange,
26
30
  open,
27
- type = 'default'
28
- }) => /*#__PURE__*/_jsx(Dialog.Root, {
29
- ...(open !== undefined && {
30
- open
31
- }),
32
- ...(onOpenChange !== undefined && {
33
- onOpenChange
34
- }),
35
- children: /*#__PURE__*/_jsx(ModalTypeProvider, {
36
- value: type,
37
- children: /*#__PURE__*/_jsx("div", {
38
- "data-type": type,
39
- ...getDataComponentAttribute('ModalV3'),
40
- children: children
31
+ type = MODAL_V3_TYPES.default
32
+ }) => {
33
+ const [internalOpen, setInternalOpen] = useState(open ?? false);
34
+ const isOpen = open ?? internalOpen;
35
+ const [bodyLockOpen, setBodyLockOpen] = useState(isOpen);
36
+ useEffect(() => {
37
+ if (isOpen) {
38
+ setBodyLockOpen(true);
39
+ } else {
40
+ const timer = setTimeout(() => setBodyLockOpen(false), parseInt(durationBase, 10));
41
+ return () => clearTimeout(timer);
42
+ }
43
+ return undefined;
44
+ }, [isOpen]);
45
+ useBodyLock(type === MODAL_V3_TYPES.chatbot && bodyLockOpen);
46
+ const handleOpenChange = details => {
47
+ if (open === undefined) {
48
+ setInternalOpen(details.open);
49
+ }
50
+ onOpenChange?.(details);
51
+ };
52
+ return /*#__PURE__*/_jsx(Dialog.Root, {
53
+ ...(open !== undefined && {
54
+ open
55
+ }),
56
+ onOpenChange: handleOpenChange,
57
+ children: /*#__PURE__*/_jsx(ModalTypeProvider, {
58
+ value: type,
59
+ children: /*#__PURE__*/_jsx("div", {
60
+ "data-type": type,
61
+ ...getDataComponentAttribute('ModalV3'),
62
+ children: children
63
+ })
41
64
  })
42
- })
43
- });
65
+ });
66
+ };
44
67
  export default BpkModalV3Root;
@@ -0,0 +1,9 @@
1
+ /**
2
+ * Locks body scroll when the modal is open, preventing background scroll and
3
+ * iOS Safari bounce effects. Restores all body styles and scroll position on
4
+ * cleanup.
5
+ * @param {boolean} isLocked - Whether the body scroll should be locked.
6
+ * @returns {void}
7
+ */
8
+ declare const useBodyLock: (isLocked: boolean) => void;
9
+ export default useBodyLock;
@@ -0,0 +1,69 @@
1
+ /*
2
+ * Backpack - Skyscanner's Design System
3
+ *
4
+ * Copyright 2016 Skyscanner Ltd
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+
19
+ import { useEffect, useRef } from 'react';
20
+
21
+ /**
22
+ * Locks body scroll when the modal is open, preventing background scroll and
23
+ * iOS Safari bounce effects. Restores all body styles and scroll position on
24
+ * cleanup.
25
+ * @param {boolean} isLocked - Whether the body scroll should be locked.
26
+ * @returns {void}
27
+ */
28
+ const useBodyLock = isLocked => {
29
+ const savedScrollYRef = useRef(0);
30
+ const savedBodyStylesRef = useRef(null);
31
+ useEffect(() => {
32
+ if (!isLocked) {
33
+ return undefined;
34
+ }
35
+ const {
36
+ body
37
+ } = document;
38
+ const currentScrollY = window.scrollY;
39
+ savedScrollYRef.current = currentScrollY;
40
+ savedBodyStylesRef.current = {
41
+ overflow: body.style.overflow || '',
42
+ position: body.style.position || '',
43
+ top: body.style.top || '',
44
+ width: body.style.width || '',
45
+ touchAction: body.style.touchAction || '',
46
+ overscrollBehavior: body.style.overscrollBehavior || ''
47
+ };
48
+ body.style.overflow = 'hidden';
49
+ body.style.position = 'fixed';
50
+ body.style.top = `-${currentScrollY}px`;
51
+ body.style.width = '100%';
52
+ body.style.touchAction = 'none';
53
+ body.style.overscrollBehavior = 'contain';
54
+ return () => {
55
+ if (savedBodyStylesRef.current) {
56
+ const saved = savedBodyStylesRef.current;
57
+ body.style.overflow = saved.overflow;
58
+ body.style.position = saved.position;
59
+ body.style.top = saved.top;
60
+ body.style.width = saved.width;
61
+ body.style.touchAction = saved.touchAction;
62
+ body.style.overscrollBehavior = saved.overscrollBehavior;
63
+ savedBodyStylesRef.current = null;
64
+ window.scrollTo(0, savedScrollYRef.current);
65
+ }
66
+ };
67
+ }, [isLocked]);
68
+ };
69
+ export default useBodyLock;
@@ -25,7 +25,7 @@ const getClassName = cssModules(STYLES);
25
25
  const BpkModalV3Scrim = () => {
26
26
  const type = useModalType();
27
27
  return /*#__PURE__*/_jsx(Dialog.Backdrop, {
28
- className: getClassName('bpk-modal-v3__scrim', type === 'full' && 'bpk-modal-v3__scrim--full'),
28
+ className: getClassName('bpk-modal-v3__scrim', type === 'full' && 'bpk-modal-v3__scrim--full', type === 'chatbot' && 'bpk-modal-v3__scrim--chatbot'),
29
29
  ...getDataComponentAttribute('ModalV3Scrim')
30
30
  });
31
31
  };
@@ -15,4 +15,4 @@
15
15
  * See the License for the specific language governing permissions and
16
16
  * limitations under the License.
17
17
  */
18
- .bpk-modal-v3__scrim{position:fixed;z-index:1100;transition:opacity 200ms ease-in-out;background-color:rgba(0,0,0,.7);opacity:0;inset:0;pointer-events:none}.bpk-modal-v3__scrim[data-state=open]{opacity:1;pointer-events:auto}.bpk-modal-v3__scrim[data-state=closed]{opacity:0}.bpk-modal-v3__scrim--full{display:none}@media(prefers-reduced-motion: reduce){.bpk-modal-v3__scrim{transition:none}}
18
+ .bpk-modal-v3__scrim{position:fixed;z-index:1100;transition:opacity 200ms ease-in-out;background-color:rgba(0,0,0,.7);opacity:0;inset:0;pointer-events:none}.bpk-modal-v3__scrim[data-state=open]{opacity:1;pointer-events:auto}.bpk-modal-v3__scrim[data-state=closed]{opacity:0}.bpk-modal-v3__scrim--full{display:none}.bpk-modal-v3__scrim--chatbot{transition:none}.bpk-modal-v3__scrim--chatbot[data-state=open]{animation:bpk-scrim-fade-in 200ms ease-in-out forwards}.bpk-modal-v3__scrim--chatbot[data-state=closed]{animation:bpk-scrim-fade-out 400ms ease-in-out both}@keyframes bpk-scrim-fade-in{from{opacity:0}to{opacity:1}}@keyframes bpk-scrim-fade-out{from{opacity:1}to{opacity:0}}@media(prefers-reduced-motion: reduce){.bpk-modal-v3__scrim{transition:none;animation:none}}
@@ -1 +1,7 @@
1
- export type BpkModalV3Type = 'default' | 'full' | 'sheet';
1
+ export declare const MODAL_V3_TYPES: {
2
+ readonly default: "default";
3
+ readonly full: "full";
4
+ readonly sheet: "sheet";
5
+ readonly chatbot: "chatbot";
6
+ };
7
+ export type BpkModalV3Type = (typeof MODAL_V3_TYPES)[keyof typeof MODAL_V3_TYPES];
@@ -1 +1,24 @@
1
- export {};
1
+ /*
2
+ * Backpack - Skyscanner's Design System
3
+ *
4
+ * Copyright 2016 Skyscanner Ltd
5
+ *
6
+ * Licensed under the Apache License, Version 2.0 (the "License");
7
+ * you may not use this file except in compliance with the License.
8
+ * You may obtain a copy of the License at
9
+ *
10
+ * http://www.apache.org/licenses/LICENSE-2.0
11
+ *
12
+ * Unless required by applicable law or agreed to in writing, software
13
+ * distributed under the License is distributed on an "AS IS" BASIS,
14
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ * See the License for the specific language governing permissions and
16
+ * limitations under the License.
17
+ */
18
+
19
+ export const MODAL_V3_TYPES = {
20
+ default: 'default',
21
+ full: 'full',
22
+ sheet: 'sheet',
23
+ chatbot: 'chatbot'
24
+ };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@skyscanner/backpack-web",
3
- "version": "42.2.0",
3
+ "version": "42.3.0",
4
4
  "description": "Backpack Design System web library",
5
5
  "repository": {
6
6
  "type": "git",
@@ -1,18 +0,0 @@
1
- /*
2
- * Backpack - Skyscanner's Design System
3
- *
4
- * Copyright 2016 Skyscanner Ltd
5
- *
6
- * Licensed under the Apache License, Version 2.0 (the "License");
7
- * you may not use this file except in compliance with the License.
8
- * You may obtain a copy of the License at
9
- *
10
- * http://www.apache.org/licenses/LICENSE-2.0
11
- *
12
- * Unless required by applicable law or agreed to in writing, software
13
- * distributed under the License is distributed on an "AS IS" BASIS,
14
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
- * See the License for the specific language governing permissions and
16
- * limitations under the License.
17
- */
18
- .bpk-modal-v3__positioner{position:fixed;display:flex;z-index:1100;justify-content:center;align-items:center;inset:0;pointer-events:none}.bpk-modal-v3__positioner--sheet{align-items:flex-end}.bpk-modal-v3__positioner--full{align-items:stretch}.bpk-modal-v3__content{position:relative;display:flex;flex-direction:column;background-color:#fff;overflow:clip;pointer-events:none}.bpk-modal-v3__content[data-state=open]{pointer-events:auto}.bpk-modal-v3__content--default{width:100%;max-width:50rem;max-height:90vh;transform:scale(0.9);transition:transform 200ms ease-in-out;border-radius:1.5rem;opacity:0;box-shadow:0px 4px 14px 0px rgba(37,32,31,.25)}@media(max-width: 32rem){.bpk-modal-v3__content--default{max-width:none;height:100%;max-height:none;transform:translateY(100%);border-radius:0;box-shadow:none}.bpk-modal-v3__content--default[data-state=open]{transform:translateY(0)}.bpk-modal-v3__content--default[data-state=closed]{transform:translateY(100%)}}.bpk-modal-v3__content--default[data-state=open]{transform:scale(1);opacity:1}.bpk-modal-v3__content--default[data-state=closed]{transform:scale(0.9);opacity:0}.bpk-modal-v3__content--sheet{width:100%;height:fit-content;max-height:100dvh;transform:translateY(100%);transition:opacity 400ms cubic-bezier(0.5, 0, 0, 1),transform 400ms cubic-bezier(0.5, 0, 0, 1);border-radius:1.5rem 1.5rem 0 0;opacity:0;box-shadow:0px 4px 14px 0px rgba(37,32,31,.25)}.bpk-modal-v3__content--sheet[data-state=open]{transform:translateY(0);opacity:1}.bpk-modal-v3__content--sheet[data-state=closed]{transform:translateY(100%);opacity:0}.bpk-modal-v3__content--full{width:100%;height:100%;transform:translateY(100%);transition:opacity 400ms cubic-bezier(0.5, 0, 0, 1),transform 400ms cubic-bezier(0.5, 0, 0, 1);border-radius:0;opacity:0}.bpk-modal-v3__content--full[data-state=open]{transform:translateY(0);opacity:1}.bpk-modal-v3__content--full[data-state=closed]{transform:translateY(100%);opacity:0}@media(prefers-reduced-motion: reduce){.bpk-modal-v3__content--default{transform:scale(1);transition:none;opacity:1}}@media(prefers-reduced-motion: reduce)and (max-width: 32rem){.bpk-modal-v3__content--default{transform:translateY(0)}}@media(prefers-reduced-motion: reduce){.bpk-modal-v3__content--sheet,.bpk-modal-v3__content--full{transform:translateY(0);transition:none;opacity:1}}