diff --git a/apps/docs/docs/widgets/bookmarks/index.mdx b/apps/docs/docs/widgets/bookmarks/index.mdx
index a8808eb6f..fbab1f89b 100644
--- a/apps/docs/docs/widgets/bookmarks/index.mdx
+++ b/apps/docs/docs/widgets/bookmarks/index.mdx
@@ -15,10 +15,12 @@ import { bookmarksWidget } from ".";
The Bookmarks widget keeps direct URLs and Homarr Apps in one ordered list. URLs do not require an App record; Homarr
uses the site's favicon when available. Choose adaptive, compact-grid, or other layouts from the widget configuration.
-Adaptive, vertical, and grid layouts keep larger cards when the configured bookmarks fit, then reduce card height and
-spacing to show as many bookmarks as possible before scrolling. Horizontal uses a compact, centered scrolling row with
-narrower cards in one-row widgets. Horizontal, compact-grid, and icon-only layouts keep their gaps tight. Compact grid
-also preserves its configured columns when the dashboard is scaled.
+Vertical uses consistent compact rows and keeps bookmark names visible whenever the widget is wide enough, regardless
+of how many bookmarks are configured. Adaptive and grid layouts reduce card height and spacing to show as many
+bookmarks as possible before scrolling. Horizontal uses a compact, centered scrolling row with narrower cards in
+one-row widgets. Horizontal, vertical, compact-grid, and icon-only layouts keep their gaps tight. Compact grid also
+preserves its configured columns when the dashboard is scaled. Bookmark cards, icons, text, and gaps keep the same
+visual density when a low-column dashboard is enlarged to fill the screen.
### Screenshots
diff --git a/apps/docs/docs/widgets/bookmarks/index.ts b/apps/docs/docs/widgets/bookmarks/index.ts
index bfc971457..c8d04653b 100644
--- a/apps/docs/docs/widgets/bookmarks/index.ts
+++ b/apps/docs/docs/widgets/bookmarks/index.ts
@@ -17,7 +17,7 @@ export const bookmarksWidget: WidgetDefinition = {
{
name: "Layout",
description:
- "How bookmarks use the available widget space. Layouts stay compact and reduce card size when needed.",
+ "How bookmarks use the available widget space. Vertical keeps compact rows and stable title visibility.",
values: { type: "select", options: ["Adaptive", "Vertical", "Horizontal", "Grid", "Compact grid", "Icons"] },
defaultValue: "Adaptive",
},
diff --git a/packages/widgets/src/bookmarks/bookmarks-widget.tsx b/packages/widgets/src/bookmarks/bookmarks-widget.tsx
index 968b47303..01fac1958 100644
--- a/packages/widgets/src/bookmarks/bookmarks-widget.tsx
+++ b/packages/widgets/src/bookmarks/bookmarks-widget.tsx
@@ -1,5 +1,6 @@
"use client";
+import type { CSSProperties } from "react";
import { useMemo, useState } from "react";
import {
Avatar,
@@ -144,9 +145,21 @@ export default function BookmarksWidget({
if (appIds.length > 0 && isInitialWidgetQueryPending(appsQuery)) return ;
const isTight = responsiveHeight < 120;
+ let compactStyle: CSSProperties | undefined;
+ if (!advanced && Number.isFinite(displayScale) && displayScale > 1) {
+ // Low-column boards zoom the canvas above 100%. Keep bookmark controls at their intended physical size.
+ // The spacing and font tokens are rebound here because their inherited values resolve at the canvas level.
+ compactStyle = {
+ "--board-canvas-ui-scale": 1 / displayScale,
+ "--mantine-scale": 1 / displayScale,
+ "--mantine-font-size-xxs": "calc(0.6875rem * var(--board-canvas-ui-scale))",
+ "--mantine-spacing-sm": "calc(0.75rem * var(--board-canvas-ui-scale))",
+ "--mantine-spacing-xs": "calc(0.625rem * var(--board-canvas-ui-scale))",
+ } as CSSProperties;
+ }
return (
-
+
{options.title.length > 0 ? (
{options.title}
diff --git a/packages/widgets/src/bookmarks/layout.ts b/packages/widgets/src/bookmarks/layout.ts
index bd08ac273..25efd59f5 100644
--- a/packages/widgets/src/bookmarks/layout.ts
+++ b/packages/widgets/src/bookmarks/layout.ts
@@ -246,23 +246,15 @@ export const getBookmarkDisplayPlan = ({
}
if (layout === "column") {
- const densitySettings = getBookmarkDensitySettings({
- columns: 1,
- gap,
- height: normalizedHeight,
- heightProperty: "columnItemHeight",
- itemCount: count,
- preferredSettings: heightSettings,
- });
return {
columns: 1,
horizontalScroll: false,
- itemGap: getBookmarkDensityGap(gap, densitySettings),
- itemHeight: densitySettings.columnItemHeight,
+ itemGap: Math.min(gap, 4),
+ itemHeight: 32,
itemWidth: width,
orientation: "horizontal",
- showHostname: widthSettings.showHostname && densitySettings.showHostname,
- showTitle: widthSettings.showTitle && densitySettings.showTitle,
+ showHostname: widthSettings.showHostname,
+ showTitle: widthSettings.showTitle,
};
}