1 parent
53b7be3c6f
commit
906ea8ba26
8 files changed
+104
-16
No files matched your search
@@ -331,30 +331,37 @@ export function shouldScrollActiveSidebarSelection(options: { activeTabId: strin
|
||||
return options.activeTabId !== options.previousActiveTabId || (options.autoSelectEnabled && options.previousAutoSelectEnabled === false);
|
||||
}
|
||||
|
||||
// nearest is used for passive auto-selection; smart keeps context for explicit locate actions.
|
||||
export type SidebarNodeScrollAlign = "nearest" | "top" | "smart";
|
||||
// nearest is used for passive auto-selection; smart keeps context for the existing toolbar action.
|
||||
export type SidebarNodeScrollAlign = "nearest" | "top" | "smart" | "center";
|
||||
|
||||
export function scrollTopForSidebarNode(options: { index: number; currentScrollTop: number; viewportHeight: number; rowHeight?: number; topOcclusionHeight?: number; align?: SidebarNodeScrollAlign }): number {
|
||||
export function scrollTopForSidebarNode(options: { index: number; currentScrollTop: number; viewportHeight: number; scrollHeight?: number; rowHeight?: number; topOcclusionHeight?: number; align?: SidebarNodeScrollAlign }): number {
|
||||
const rowHeight = options.rowHeight ?? SIDEBAR_TREE_ROW_HEIGHT;
|
||||
if (options.index < 0 || options.viewportHeight <= 0) return options.currentScrollTop;
|
||||
|
||||
const rowTop = options.index * rowHeight;
|
||||
const rowBottom = rowTop + rowHeight;
|
||||
const topOcclusionHeight = options.topOcclusionHeight ?? 0;
|
||||
if (options.align === "top") return Math.max(0, rowTop - topOcclusionHeight);
|
||||
const maxScrollTop = options.scrollHeight == null ? Number.POSITIVE_INFINITY : Math.max(0, options.scrollHeight - options.viewportHeight);
|
||||
const clampScrollTop = (value: number) => Math.max(0, Math.min(maxScrollTop, value));
|
||||
if (options.align === "top") return clampScrollTop(rowTop - topOcclusionHeight);
|
||||
if (options.align === "smart") {
|
||||
// Similar to IDE Locate: place the target around the upper third of the viewport.
|
||||
const availableViewportHeight = Math.max(rowHeight, options.viewportHeight - topOcclusionHeight);
|
||||
const smartOffset = Math.max(0, (availableViewportHeight - rowHeight) / 3);
|
||||
return Math.max(0, Math.round(rowTop - topOcclusionHeight - smartOffset));
|
||||
return clampScrollTop(Math.round(rowTop - topOcclusionHeight - smartOffset));
|
||||
}
|
||||
if (options.align === "center") {
|
||||
const availableViewportHeight = Math.max(rowHeight, options.viewportHeight - topOcclusionHeight);
|
||||
const centerOffset = Math.max(0, (availableViewportHeight - rowHeight) / 2);
|
||||
return clampScrollTop(Math.round(rowTop - topOcclusionHeight - centerOffset));
|
||||
}
|
||||
|
||||
const viewportTop = options.currentScrollTop + topOcclusionHeight;
|
||||
const viewportBottom = options.currentScrollTop + options.viewportHeight;
|
||||
|
||||
if (rowTop < viewportTop) return Math.max(0, rowTop - topOcclusionHeight);
|
||||
if (rowBottom > viewportBottom) return Math.max(0, rowBottom - options.viewportHeight);
|
||||
return options.currentScrollTop;
|
||||
if (rowTop < viewportTop) return clampScrollTop(rowTop - topOcclusionHeight);
|
||||
if (rowBottom > viewportBottom) return clampScrollTop(rowBottom - options.viewportHeight);
|
||||
return clampScrollTop(options.currentScrollTop);
|
||||
}
|
||||
|
||||
export function findNodePathForActiveTab(tab: QueryTab | undefined | null, treeNodes: readonly TreeNode[]): TreeNode[] | null {
|
||||
|
||||
Reference in new issue
Block a user