@danxbot/ui 20.19.0 → 20.20.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.
@@ -116,7 +116,7 @@ export { Board, BoardColumn, BoardCard, BoardCardSurface, type BoardProps, type
116
116
  export { buildBoardModel, resolveMove, applyBoardMoves, useBoard, moveAnchor, columnLength, positionInColumn, type BoardModel, type MoveAnchor, type UseBoardResult, } from "./lib/board";
117
117
  export type { BoardAccessors, BoardColumnDef, BoardEdge, BoardColumnId, BoardColumnModel, BoardItemId, BoardMove, BoardMoveTarget, BoardMoveRequest, BoardMoveSource, BoardMoveVerdict, BoardReorderLabels, UseBoardOptions, } from "./lib/board";
118
118
  export { PagedWindowList, type PagedWindowItemPosition, type PagedWindowListProps, type PagedWindowStrings, } from "./components/PagedWindowList";
119
- export { PagedWindowStore, usePagedWindow, windowPageNumbers, type LoadCount, type LoadPage, type LoadPageContext, type PageResponse, type PageSnapshot, type PageStatus, type PagedWindow, type PagedWindowMode, type PagedWindowOptions, type PagedWindowSnapshot, type UsePagedWindowOptions, } from "./lib/paged-window";
119
+ export { PAGED_WINDOW_SETTLE_MS, PagedWindowStore, usePagedWindow, windowPageNumbers, type LoadCount, type LoadPage, type LoadPageContext, type PageResponse, type PageSnapshot, type PageStatus, type PagedWindow, type PagedWindowMode, type PagedWindowOptions, type PagedWindowSnapshot, type UsePagedWindowOptions, } from "./lib/paged-window";
120
120
  export type { MessageRole, MessagePart, TextPart, CodePart, ReasoningPart, ToolPart, ToolStatus, FilePart, ComponentPart, ChatFile, ChatMessage, RenderContext, PartRenderer, PartRenderers, ChatComponentRenderer, ChatComponents, } from "./components/chat/types";
121
121
  export { Chat, ChatPopover, type ChatProps, type ChatPopoverProps, type ChatSurface, } from "./components/chat/Chat";
122
122
  export { Message, MessagePartView, ToolCall, type MessageProps, type MessageAction, type MessagePartViewProps, type ToolCallProps, } from "./components/chat/Message";
@@ -1,2 +1,2 @@
1
- export { PagedWindowStore, windowPageNumbers, type LoadCount, type LoadPage, type LoadPageContext, type PageResponse, type PageSnapshot, type PageStatus, type PagedWindowMode, type PagedWindowOptions, type PagedWindowSnapshot, } from "./store";
1
+ export { PAGED_WINDOW_SETTLE_MS, PagedWindowStore, windowPageNumbers, type LoadCount, type LoadPage, type LoadPageContext, type PageResponse, type PageSnapshot, type PageStatus, type PagedWindowMode, type PagedWindowOptions, type PagedWindowSnapshot, } from "./store";
2
2
  export { usePagedWindow, type PagedWindow, type UsePagedWindowOptions } from "./use-paged-window";
@@ -12,6 +12,8 @@ export type LoadPage<T> = (page: number, context: LoadPageContext) => Promise<Pa
12
12
  /** Answers the list's length alone — no items. What a hidden (`count` mode) lane asks. */
13
13
  export type LoadCount = (context: LoadPageContext) => Promise<number>;
14
14
  export type PagedWindowMode = "pages" | "count";
15
+ /** How long the viewer's page must stay put before the window moves to it, in ms. */
16
+ export declare const PAGED_WINDOW_SETTLE_MS = 200;
15
17
  export type PageStatus = "loading" | "ready" | "error";
16
18
  export interface PageSnapshot<T> {
17
19
  page: number;
@@ -54,6 +56,12 @@ export interface PagedWindowOptions<T> {
54
56
  loadCount?: LoadCount;
55
57
  /** @default "pages" */
56
58
  mode?: PagedWindowMode;
59
+ /**
60
+ * How long the viewer's page must stay put before the window moves to it; 0
61
+ * moves it synchronously. A negative or fractional value throws.
62
+ * @default PAGED_WINDOW_SETTLE_MS
63
+ */
64
+ settleMs?: number;
57
65
  }
58
66
  /**
59
67
  * The pages to hold for an anchor: `windowPages` of them centred on it (the
@@ -64,13 +72,17 @@ export declare function windowPageNumbers(anchorPage: number, pageCount: number,
64
72
  export declare class PagedWindowStore<T> {
65
73
  private readonly pageSize;
66
74
  private readonly windowPages;
75
+ private readonly settleMs;
67
76
  private loadPage;
68
77
  private loadCount;
69
78
  private held;
70
79
  private total;
80
+ /** Where the viewer is; moves the instant they do. */
71
81
  private anchor;
72
- /** The anchor the held pages were last synced to; differs from `anchor` only while frozen. */
82
+ /** The anchor the held pages were last synced to; differs from `anchor` while the viewer is still moving, or frozen. */
73
83
  private appliedAnchor;
84
+ /** Moves the window to `anchor` once it has been still for `settleMs`; null when no move is waiting. */
85
+ private settleTimer;
74
86
  private mode;
75
87
  private frozen;
76
88
  private epoch;
@@ -85,7 +97,7 @@ export declare class PagedWindowStore<T> {
85
97
  private countError;
86
98
  private snapshot;
87
99
  private listeners;
88
- constructor({ pageSize, windowPages, loadPage, loadCount, mode }: PagedWindowOptions<T>);
100
+ constructor({ pageSize, windowPages, loadPage, loadCount, mode, settleMs, }: PagedWindowOptions<T>);
89
101
  /**
90
102
  * Replace the loaders. The React binding calls this after every commit so a
91
103
  * consumer's loaders can close over fresh state without the store being
@@ -95,7 +107,10 @@ export declare class PagedWindowStore<T> {
95
107
  setLoaders(loadPage: LoadPage<T>, loadCount: LoadCount | undefined): void;
96
108
  getSnapshot: () => PagedWindowSnapshot<T>;
97
109
  subscribe: (listener: () => void) => (() => void);
98
- /** The viewer moved to another page. Ignored while frozen, applied on thaw. */
110
+ /**
111
+ * The viewer moved to another page. The window follows once they have stayed
112
+ * there for `settleMs`; while frozen it follows on thaw.
113
+ */
99
114
  setAnchorPage(page: number): void;
100
115
  /**
101
116
  * While true nothing about the window changes: it neither loads nor drops
@@ -130,7 +145,16 @@ export declare class PagedWindowStore<T> {
130
145
  private wanted;
131
146
  /** Bring the held pages to the wanted ones — unless frozen, when that waits for the thaw. */
132
147
  private sync;
133
- /** `force` is `reset()`'s alone: it brings the window to its (new) list even while frozen. */
148
+ /** The viewer has settled on `anchor`: the window moves to it, in one step. */
149
+ private applyAnchor;
150
+ private clearSettle;
151
+ /**
152
+ * Moves the held pages to the window around `appliedAnchor` — which only
153
+ * `applyAnchor`, `thaw` and `reset` move, so a response arriving while the
154
+ * viewer is still moving brings in no page of the unsettled position.
155
+ * `force` is `reset()`'s alone: it brings the window to its (new) list even
156
+ * while frozen.
157
+ */
134
158
  private reconcile;
135
159
  /** Everything the frozen window put off, in the order the header promises. */
136
160
  private thaw;
@@ -34,8 +34,14 @@ export interface PagedWindow<T> extends PagedWindowSnapshot<T> {
34
34
  * view which ones to show. `loadPage` answers one page AND the list's current
35
35
  * length, so the scrollbar can span `total` before most of it is loaded.
36
36
  *
37
+ * The window moves to the viewer's page only after it has stayed put for
38
+ * `settleMs` (200 ms by default), so a fast scroll loads the pages it lands
39
+ * on, never the ones it passes (DX-4614); a read for a page that leaves the
40
+ * window is aborted through its `signal`, and an aborted read is never an error.
41
+ *
37
42
  * `pageSize` and `windowPages` are fixed for the life of the hook: changing one
38
43
  * means every held page is cut differently, which is a different list — give it
39
- * a new `queryKey` and a new mount instead. It throws rather than guessing.
44
+ * a new `queryKey` and a new mount instead. `settleMs` is fixed too: the store
45
+ * reads it once. All three throw rather than guess.
40
46
  */
41
- export declare function usePagedWindow<T>({ pageSize, windowPages, loadPage, loadCount, queryKey, mode, }: UsePagedWindowOptions<T>): PagedWindow<T>;
47
+ export declare function usePagedWindow<T>({ pageSize, windowPages, loadPage, loadCount, queryKey, mode, settleMs, }: UsePagedWindowOptions<T>): PagedWindow<T>;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@danxbot/ui",
3
- "version": "20.19.0",
3
+ "version": "20.20.0",
4
4
  "type": "module",
5
5
  "description": "Danxbot — a domain-agnostic React design system with motion as a first-class primitive.",
6
6
  "license": "MIT",