@wise/dynamic-flow-client 4.19.1 → 4.19.3-experimental-6e22f2a

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/build/main.js CHANGED
@@ -1245,7 +1245,7 @@ var CoreRootRenderer = {
1245
1245
  canRenderType: "root",
1246
1246
  render: ({ children, childrenProps }) => {
1247
1247
  const [stepProps] = findRendererPropsByType(childrenProps, "step");
1248
- return /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { id: stepProps == null ? void 0 : stepProps.id, className: "dynamic-flow", children });
1248
+ return /* @__PURE__ */ (0, import_jsx_runtime4.jsx)("div", { id: stepProps == null ? void 0 : stepProps.id, className: "dynamic-flow-step", children });
1249
1249
  }
1250
1250
  };
1251
1251
 
@@ -2258,7 +2258,7 @@ var getInputUpdateFunction = (updateComponent) => {
2258
2258
  };
2259
2259
 
2260
2260
  // src/revamp/domain/components/RootDomainComponent.ts
2261
- var createRootDomainComponent = (updateComponent) => {
2261
+ var createRootDomainComponent = (updateComponent, scrollToTop) => {
2262
2262
  const update = getInputUpdateFunction(updateComponent);
2263
2263
  const rootComponent = {
2264
2264
  type: "root",
@@ -2319,10 +2319,12 @@ var createRootDomainComponent = (updateComponent) => {
2319
2319
  var _a;
2320
2320
  (_a = this.stepComponent) == null ? void 0 : _a.stop();
2321
2321
  },
2322
- setStep(stepComponent) {
2322
+ setStep(step) {
2323
+ const scrollAfterUpdate = getScrollAfterUpdate(step, this.stepComponent, scrollToTop);
2323
2324
  this._update((draft) => {
2324
- draft.stepComponent = stepComponent;
2325
+ draft.stepComponent = step;
2325
2326
  });
2327
+ scrollAfterUpdate == null ? void 0 : scrollAfterUpdate();
2326
2328
  },
2327
2329
  getRefreshUrl() {
2328
2330
  var _a, _b, _c, _d;
@@ -2331,6 +2333,16 @@ var createRootDomainComponent = (updateComponent) => {
2331
2333
  };
2332
2334
  return rootComponent;
2333
2335
  };
2336
+ var getScrollAfterUpdate = (newStep, currentStep, scrollToTop) => {
2337
+ if (!currentStep) {
2338
+ return void 0;
2339
+ }
2340
+ const isNewStep = newStep.uid !== currentStep.uid;
2341
+ const hasNewError = newStep.error != null && newStep.error !== currentStep.error;
2342
+ const shouldScroll = isNewStep || hasNewError;
2343
+ const scrollBehavior = hasNewError ? "smooth" : "instant";
2344
+ return shouldScroll ? () => scrollToTop(scrollBehavior) : void 0;
2345
+ };
2334
2346
 
2335
2347
  // src/revamp/domain/components/ModalComponent.ts
2336
2348
  var createModalContentComponent = (modalProps, updateComponent) => {
@@ -7168,13 +7180,16 @@ function useDynamicFlowCore(props) {
7168
7180
  const onError = useStableCallback(rest.onError);
7169
7181
  const onEvent = useStableCallback(rest.onEvent);
7170
7182
  const onLog = useStableCallback(rest.onLog);
7183
+ const scrollToTop = useStableCallback(props.scrollToTop);
7171
7184
  const { formatMessage, locale } = (0, import_react_intl7.useIntl)();
7172
7185
  const getErrorMessageFunctions = (0, import_react3.useMemo)(
7173
7186
  () => getSchemaErrorMessageFunction(formatMessage, locale),
7174
7187
  [formatMessage, locale]
7175
7188
  );
7176
7189
  const rerender = useRerender();
7177
- const rootComponentRef = (0, import_react3.useRef)(createRootDomainComponent(rerender));
7190
+ const rootComponentRef = (0, import_react3.useRef)(
7191
+ createRootDomainComponent(rerender, scrollToTop)
7192
+ );
7178
7193
  const stepCount = (0, import_react3.useRef)(0);
7179
7194
  const stepRef = (0, import_react3.useRef)(initialStep != null ? initialStep : null);
7180
7195
  const etagRef = (0, import_react3.useRef)(null);
@@ -7506,10 +7521,18 @@ var useRerender = () => {
7506
7521
 
7507
7522
  // src/revamp/DynamicFlowCore.tsx
7508
7523
  var import_jsx_runtime6 = require("react/jsx-runtime");
7524
+ var className = "dynamic-flow";
7509
7525
  function DynamicFlowCore(props) {
7510
7526
  var _a;
7511
- const { rootComponent } = useDynamicFlowCore(props);
7512
- const { renderers, httpClient, onEvent, onError, onLog } = props;
7527
+ const { flowId, renderers, httpClient, onEvent, onError, onLog } = props;
7528
+ const normalisedFlowId = flowId.replace(" ", "-");
7529
+ const { rootComponent } = useDynamicFlowCore(__spreadProps(__spreadValues({}, props), {
7530
+ scrollToTop: (behavior) => {
7531
+ var _a2;
7532
+ const element = document.querySelector(`div#${normalisedFlowId}.${className}`);
7533
+ (_a2 = element == null ? void 0 : element.scrollIntoView) == null ? void 0 : _a2.call(element, { behavior });
7534
+ }
7535
+ }));
7513
7536
  const render = (0, import_react4.useMemo)(
7514
7537
  () => getRenderFunction([CoreRootRenderer, CoreContainerRenderer, ...renderers]),
7515
7538
  [renderers]
@@ -7529,7 +7552,7 @@ function DynamicFlowCore(props) {
7529
7552
  onError == null ? void 0 : onError(error);
7530
7553
  onLog == null ? void 0 : onLog("error", "Dynamic Flow - ErrorBoundary", { errorMessage: getErrorMessage(error) });
7531
7554
  },
7532
- children: render(tree)
7555
+ children: /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { id: normalisedFlowId, className, children: render(tree) })
7533
7556
  }
7534
7557
  );
7535
7558
  }
@@ -8885,7 +8908,7 @@ function DynamicButtonWithoutBehavior(props) {
8885
8908
  const type = getButtonType(component.context, componentAction);
8886
8909
  const priority = getButtonPriority(component.control, componentAction);
8887
8910
  const { loading } = useDynamicFlow();
8888
- const className = getMargin(component.margin || "md");
8911
+ const className2 = getMargin(component.margin || "md");
8889
8912
  const disabled = loading || component.disabled || (componentAction == null ? void 0 : componentAction.disabled);
8890
8913
  const title = (_b = (_a = component.title) != null ? _a : componentAction == null ? void 0 : componentAction.title) != null ? _b : "";
8891
8914
  const onClick = () => {
@@ -8900,7 +8923,7 @@ function DynamicButtonWithoutBehavior(props) {
8900
8923
  type: priority === "tertiary" ? void 0 : type,
8901
8924
  priority,
8902
8925
  block: true,
8903
- className,
8926
+ className: className2,
8904
8927
  disabled,
8905
8928
  onClick,
8906
8929
  children: title
@@ -8913,7 +8936,7 @@ function DynamicButtonWithBehavior(props) {
8913
8936
  const type = getButtonTypeFromContext(component.context);
8914
8937
  const priority = (_a = component.control) != null ? _a : "secondary";
8915
8938
  const { loading } = useDynamicFlow();
8916
- const className = getMargin(component.margin || "md");
8939
+ const className2 = getMargin(component.margin || "md");
8917
8940
  const disabled = loading || component.disabled;
8918
8941
  const title = (_b = component.title) != null ? _b : "";
8919
8942
  const onClick = () => {
@@ -8952,7 +8975,7 @@ function DynamicButtonWithBehavior(props) {
8952
8975
  type: priority === "tertiary" ? void 0 : type,
8953
8976
  priority,
8954
8977
  block: true,
8955
- className,
8978
+ className: className2,
8956
8979
  disabled,
8957
8980
  onClick,
8958
8981
  children: title
@@ -9042,8 +9065,8 @@ var DynamicDecision_default = DynamicDecision;
9042
9065
  var import_jsx_runtime21 = require("react/jsx-runtime");
9043
9066
  var DynamicDivider = ({ component }) => {
9044
9067
  const margin = getMargin(component.margin);
9045
- const className = `m-t-0 ${margin}`;
9046
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("hr", { className });
9068
+ const className2 = `m-t-0 ${margin}`;
9069
+ return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("hr", { className: className2 });
9047
9070
  };
9048
9071
  var DynamicDivider_default = DynamicDivider;
9049
9072
 
package/build/main.mjs CHANGED
@@ -1202,7 +1202,7 @@ var CoreRootRenderer = {
1202
1202
  canRenderType: "root",
1203
1203
  render: ({ children, childrenProps }) => {
1204
1204
  const [stepProps] = findRendererPropsByType(childrenProps, "step");
1205
- return /* @__PURE__ */ jsx4("div", { id: stepProps == null ? void 0 : stepProps.id, className: "dynamic-flow", children });
1205
+ return /* @__PURE__ */ jsx4("div", { id: stepProps == null ? void 0 : stepProps.id, className: "dynamic-flow-step", children });
1206
1206
  }
1207
1207
  };
1208
1208
 
@@ -2215,7 +2215,7 @@ var getInputUpdateFunction = (updateComponent) => {
2215
2215
  };
2216
2216
 
2217
2217
  // src/revamp/domain/components/RootDomainComponent.ts
2218
- var createRootDomainComponent = (updateComponent) => {
2218
+ var createRootDomainComponent = (updateComponent, scrollToTop) => {
2219
2219
  const update = getInputUpdateFunction(updateComponent);
2220
2220
  const rootComponent = {
2221
2221
  type: "root",
@@ -2276,10 +2276,12 @@ var createRootDomainComponent = (updateComponent) => {
2276
2276
  var _a;
2277
2277
  (_a = this.stepComponent) == null ? void 0 : _a.stop();
2278
2278
  },
2279
- setStep(stepComponent) {
2279
+ setStep(step) {
2280
+ const scrollAfterUpdate = getScrollAfterUpdate(step, this.stepComponent, scrollToTop);
2280
2281
  this._update((draft) => {
2281
- draft.stepComponent = stepComponent;
2282
+ draft.stepComponent = step;
2282
2283
  });
2284
+ scrollAfterUpdate == null ? void 0 : scrollAfterUpdate();
2283
2285
  },
2284
2286
  getRefreshUrl() {
2285
2287
  var _a, _b, _c, _d;
@@ -2288,6 +2290,16 @@ var createRootDomainComponent = (updateComponent) => {
2288
2290
  };
2289
2291
  return rootComponent;
2290
2292
  };
2293
+ var getScrollAfterUpdate = (newStep, currentStep, scrollToTop) => {
2294
+ if (!currentStep) {
2295
+ return void 0;
2296
+ }
2297
+ const isNewStep = newStep.uid !== currentStep.uid;
2298
+ const hasNewError = newStep.error != null && newStep.error !== currentStep.error;
2299
+ const shouldScroll = isNewStep || hasNewError;
2300
+ const scrollBehavior = hasNewError ? "smooth" : "instant";
2301
+ return shouldScroll ? () => scrollToTop(scrollBehavior) : void 0;
2302
+ };
2291
2303
 
2292
2304
  // src/revamp/domain/components/ModalComponent.ts
2293
2305
  var createModalContentComponent = (modalProps, updateComponent) => {
@@ -7125,13 +7137,16 @@ function useDynamicFlowCore(props) {
7125
7137
  const onError = useStableCallback(rest.onError);
7126
7138
  const onEvent = useStableCallback(rest.onEvent);
7127
7139
  const onLog = useStableCallback(rest.onLog);
7140
+ const scrollToTop = useStableCallback(props.scrollToTop);
7128
7141
  const { formatMessage, locale } = useIntl2();
7129
7142
  const getErrorMessageFunctions = useMemo(
7130
7143
  () => getSchemaErrorMessageFunction(formatMessage, locale),
7131
7144
  [formatMessage, locale]
7132
7145
  );
7133
7146
  const rerender = useRerender();
7134
- const rootComponentRef = useRef2(createRootDomainComponent(rerender));
7147
+ const rootComponentRef = useRef2(
7148
+ createRootDomainComponent(rerender, scrollToTop)
7149
+ );
7135
7150
  const stepCount = useRef2(0);
7136
7151
  const stepRef = useRef2(initialStep != null ? initialStep : null);
7137
7152
  const etagRef = useRef2(null);
@@ -7463,10 +7478,18 @@ var useRerender = () => {
7463
7478
 
7464
7479
  // src/revamp/DynamicFlowCore.tsx
7465
7480
  import { jsx as jsx6 } from "react/jsx-runtime";
7481
+ var className = "dynamic-flow";
7466
7482
  function DynamicFlowCore(props) {
7467
7483
  var _a;
7468
- const { rootComponent } = useDynamicFlowCore(props);
7469
- const { renderers, httpClient, onEvent, onError, onLog } = props;
7484
+ const { flowId, renderers, httpClient, onEvent, onError, onLog } = props;
7485
+ const normalisedFlowId = flowId.replace(" ", "-");
7486
+ const { rootComponent } = useDynamicFlowCore(__spreadProps(__spreadValues({}, props), {
7487
+ scrollToTop: (behavior) => {
7488
+ var _a2;
7489
+ const element = document.querySelector(`div#${normalisedFlowId}.${className}`);
7490
+ (_a2 = element == null ? void 0 : element.scrollIntoView) == null ? void 0 : _a2.call(element, { behavior });
7491
+ }
7492
+ }));
7470
7493
  const render = useMemo2(
7471
7494
  () => getRenderFunction([CoreRootRenderer, CoreContainerRenderer, ...renderers]),
7472
7495
  [renderers]
@@ -7486,7 +7509,7 @@ function DynamicFlowCore(props) {
7486
7509
  onError == null ? void 0 : onError(error);
7487
7510
  onLog == null ? void 0 : onLog("error", "Dynamic Flow - ErrorBoundary", { errorMessage: getErrorMessage(error) });
7488
7511
  },
7489
- children: render(tree)
7512
+ children: /* @__PURE__ */ jsx6("div", { id: normalisedFlowId, className, children: render(tree) })
7490
7513
  }
7491
7514
  );
7492
7515
  }
@@ -8842,7 +8865,7 @@ function DynamicButtonWithoutBehavior(props) {
8842
8865
  const type = getButtonType(component.context, componentAction);
8843
8866
  const priority = getButtonPriority(component.control, componentAction);
8844
8867
  const { loading } = useDynamicFlow();
8845
- const className = getMargin(component.margin || "md");
8868
+ const className2 = getMargin(component.margin || "md");
8846
8869
  const disabled = loading || component.disabled || (componentAction == null ? void 0 : componentAction.disabled);
8847
8870
  const title = (_b = (_a = component.title) != null ? _a : componentAction == null ? void 0 : componentAction.title) != null ? _b : "";
8848
8871
  const onClick = () => {
@@ -8857,7 +8880,7 @@ function DynamicButtonWithoutBehavior(props) {
8857
8880
  type: priority === "tertiary" ? void 0 : type,
8858
8881
  priority,
8859
8882
  block: true,
8860
- className,
8883
+ className: className2,
8861
8884
  disabled,
8862
8885
  onClick,
8863
8886
  children: title
@@ -8870,7 +8893,7 @@ function DynamicButtonWithBehavior(props) {
8870
8893
  const type = getButtonTypeFromContext(component.context);
8871
8894
  const priority = (_a = component.control) != null ? _a : "secondary";
8872
8895
  const { loading } = useDynamicFlow();
8873
- const className = getMargin(component.margin || "md");
8896
+ const className2 = getMargin(component.margin || "md");
8874
8897
  const disabled = loading || component.disabled;
8875
8898
  const title = (_b = component.title) != null ? _b : "";
8876
8899
  const onClick = () => {
@@ -8909,7 +8932,7 @@ function DynamicButtonWithBehavior(props) {
8909
8932
  type: priority === "tertiary" ? void 0 : type,
8910
8933
  priority,
8911
8934
  block: true,
8912
- className,
8935
+ className: className2,
8913
8936
  disabled,
8914
8937
  onClick,
8915
8938
  children: title
@@ -8999,8 +9022,8 @@ var DynamicDecision_default = DynamicDecision;
8999
9022
  import { jsx as jsx21 } from "react/jsx-runtime";
9000
9023
  var DynamicDivider = ({ component }) => {
9001
9024
  const margin = getMargin(component.margin);
9002
- const className = `m-t-0 ${margin}`;
9003
- return /* @__PURE__ */ jsx21("hr", { className });
9025
+ const className2 = `m-t-0 ${margin}`;
9026
+ return /* @__PURE__ */ jsx21("hr", { className: className2 });
9004
9027
  };
9005
9028
  var DynamicDivider_default = DynamicDivider;
9006
9029
 
@@ -1,6 +1,6 @@
1
1
  import { Model } from '@wise/dynamic-flow-types';
2
2
  import { AnalyticsEventDispatcher } from '../features/events';
3
- import { BaseComponent, DomainComponent, LoadingState, LocalValue, SchemaComponent, UpdateComponent } from '../types';
3
+ import { BaseComponent, DomainComponent, LoadingState, LocalValue, SchemaComponent, ScrollToTop, UpdateComponent } from '../types';
4
4
  import { ModalComponent } from './ModalComponent';
5
5
  import { StepDomainComponent } from './step/StepDomainComponent';
6
6
  export type RootDomainComponent = BaseComponent & {
@@ -25,4 +25,4 @@ export type RootDomainComponent = BaseComponent & {
25
25
  setStep: (stepComponent: StepDomainComponent) => void;
26
26
  getRefreshUrl: () => string | null;
27
27
  };
28
- export declare const createRootDomainComponent: (updateComponent: UpdateComponent) => RootDomainComponent;
28
+ export declare const createRootDomainComponent: (updateComponent: UpdateComponent, scrollToTop: ScrollToTop) => RootDomainComponent;
@@ -155,6 +155,7 @@ export type BaseInputComponent<LV extends LocalValue> = BaseSchemaComponent<LV>
155
155
  onFocus: () => void;
156
156
  };
157
157
  export type UpdateComponent = () => void;
158
+ export type ScrollToTop = (behavior: ScrollBehavior) => void;
158
159
  export type OnBehavior = (behavior: Behavior) => Promise<BehaviorController>;
159
160
  export type BehaviorController = {
160
161
  abort: () => void;
@@ -1,8 +1,9 @@
1
1
  import { RootDomainComponent } from './domain/components/RootDomainComponent';
2
- import type { OnValueChange } from './domain/types';
2
+ import type { OnValueChange, ScrollToTop } from './domain/types';
3
3
  import type { DynamicFlowCoreProps } from './types';
4
4
  type UseDynamicFlowCoreProps = Omit<DynamicFlowCoreProps, 'renderers'> & {
5
5
  onValueChange?: OnValueChange;
6
+ scrollToTop?: ScrollToTop;
6
7
  onLink: (url: string) => boolean;
7
8
  };
8
9
  export declare function useDynamicFlowCore(props: UseDynamicFlowCoreProps): {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@wise/dynamic-flow-client",
3
- "version": "4.19.1",
3
+ "version": "4.19.3-experimental-6e22f2a",
4
4
  "description": "Dynamic Flow web client",
5
5
  "license": "Apache-2.0",
6
6
  "main": "./build/main.js",
@@ -37,7 +37,7 @@
37
37
  "@babel/preset-react": "7.27.1",
38
38
  "@babel/preset-typescript": "7.27.1",
39
39
  "@chromatic-com/storybook": "4.1.1",
40
- "@formatjs/cli": "^6.7.3",
40
+ "@formatjs/cli": "^6.7.4",
41
41
  "@storybook/addon-a11y": "^9.1.10",
42
42
  "@storybook/addon-docs": "^9.1.10",
43
43
  "@storybook/addon-links": "^9.1.10",
@@ -46,13 +46,14 @@
46
46
  "@testing-library/jest-dom": "6.9.1",
47
47
  "@testing-library/react": "16.3.0",
48
48
  "@testing-library/user-event": "14.6.1",
49
- "@transferwise/components": "46.111.0",
49
+ "@transferwise/components": "46.112.0",
50
50
  "@transferwise/formatting": "^2.13.4",
51
51
  "@transferwise/icons": "3.22.4",
52
+ "@transferwise/navigation-ui": "4.40.0",
52
53
  "@transferwise/neptune-css": "14.25.0",
53
54
  "@types/jest": "30.0.0",
54
- "@types/node": "22.18.8",
55
- "@types/react": "18.3.25",
55
+ "@types/node": "22.18.9",
56
+ "@types/react": "18.3.26",
56
57
  "@types/react-dom": "18.3.7",
57
58
  "@types/react-intl": "3.0.0",
58
59
  "@wise/art": "2.24.7",