From ffb576fd587668a05940f09bbd447d2742feeb0d Mon Sep 17 00:00:00 2001
From: Viktor Renkema <49148610+viktorrenkema@users.noreply.github.com>
Date: Wed, 29 Oct 2025 15:18:22 +0100
Subject: [PATCH 1/2] Revert "Support cover image heights and positioning
changes (#3758)"
This reverts commit f682df1e01c7022144ceb5da5635fd1694f29a96.
---
packages/gitbook/e2e/internal.spec.ts | 16 +--
packages/gitbook/e2e/util.ts | 7 --
.../src/components/PageBody/PageCover.tsx | 8 --
.../components/PageBody/PageCoverImage.tsx | 41 ++++---
.../src/components/PageBody/coverHeight.ts | 25 ----
.../gitbook/src/components/PageBody/index.ts | 1 -
.../components/PageBody/useCoverPosition.ts | 109 ------------------
7 files changed, 31 insertions(+), 176 deletions(-)
delete mode 100644 packages/gitbook/src/components/PageBody/coverHeight.ts
delete mode 100644 packages/gitbook/src/components/PageBody/useCoverPosition.ts
diff --git a/packages/gitbook/e2e/internal.spec.ts b/packages/gitbook/e2e/internal.spec.ts
index 8ea1a361a1..34088e136b 100644
--- a/packages/gitbook/e2e/internal.spec.ts
+++ b/packages/gitbook/e2e/internal.spec.ts
@@ -33,7 +33,6 @@ import {
headerLinks,
runTestCases,
waitForCookiesDialog,
- waitForCoverImages,
waitForNotFound,
} from './util';
@@ -907,10 +906,7 @@ const testCases: TestsCase[] = [
{
name: 'With cover',
url: 'page-options/page-with-cover',
- run: async (page) => {
- await waitForCookiesDialog(page);
- await waitForCoverImages(page);
- },
+ run: waitForCookiesDialog,
},
{
name: 'With cover for dark mode',
@@ -925,18 +921,12 @@ const testCases: TestsCase[] = [
{
name: 'With hero cover',
url: 'page-options/page-with-hero-cover',
- run: async (page) => {
- await waitForCookiesDialog(page);
- await waitForCoverImages(page);
- },
+ run: waitForCookiesDialog,
},
{
name: 'With cover and no TOC',
url: 'page-options/page-with-cover-and-no-toc',
- run: async (page) => {
- await waitForCookiesDialog(page);
- await waitForCoverImages(page);
- },
+ run: waitForCookiesDialog,
screenshot: {
waitForTOCScrolling: false,
},
diff --git a/packages/gitbook/e2e/util.ts b/packages/gitbook/e2e/util.ts
index 6b62dea8c0..c2b3a93004 100644
--- a/packages/gitbook/e2e/util.ts
+++ b/packages/gitbook/e2e/util.ts
@@ -154,13 +154,6 @@ export async function waitForNotFound(_page: Page, response: Response | null) {
expect(response?.status()).toBe(404);
}
-export async function waitForCoverImages(page: Page) {
- // Wait for cover images to exist (not the shimmer placeholder)
- await expect(page.locator('img[alt="Page cover"]').first()).toBeVisible({
- timeout: 10_000,
- });
-}
-
/**
* Transform test cases into Playwright tests and run it.
*/
diff --git a/packages/gitbook/src/components/PageBody/PageCover.tsx b/packages/gitbook/src/components/PageBody/PageCover.tsx
index 947e092802..0623310519 100644
--- a/packages/gitbook/src/components/PageBody/PageCover.tsx
+++ b/packages/gitbook/src/components/PageBody/PageCover.tsx
@@ -8,7 +8,6 @@ import { tcls } from '@/lib/tailwind';
import { assert } from 'ts-essentials';
import { PageCoverImage } from './PageCoverImage';
-import { getCoverHeight } from './coverHeight';
import defaultPageCoverSVG from './default-page-cover.svg';
const defaultPageCover = defaultPageCoverSVG as StaticImageData;
@@ -23,12 +22,6 @@ export async function PageCover(props: {
context: GitBookSiteContext;
}) {
const { as, page, cover, context } = props;
- const height = getCoverHeight(cover);
-
- if (!height) {
- return null;
- }
-
const [resolved, resolvedDark] = await Promise.all([
cover.ref ? resolveContentRef(cover.ref, context) : null,
cover.refDark ? resolveContentRef(cover.refDark, context) : null,
@@ -85,7 +78,6 @@ export async function PageCover(props: {
(null);
- if (isLoading) {
- return (
-
- );
- }
+ const container = useResizeObserver({
+ // @ts-expect-error wrong types
+ ref: containerRef,
+ });
return (
@@ -36,9 +49,10 @@ export function PageCoverImage({ imgs, y }: { imgs: Images; y: number }) {
sizes={imgs.light.sizes}
fetchPriority="high"
alt="Page cover"
- className={tcls('h-full', 'w-full', 'object-cover', imgs.dark ? 'dark:hidden' : '')}
+ className={tcls('w-full', 'object-cover', imgs.dark ? 'dark:hidden' : '')}
style={{
- objectPosition: `50% ${objectPositionY}%`,
+ aspectRatio: `${PAGE_COVER_SIZE.width}/${PAGE_COVER_SIZE.height}`,
+ objectPosition: `50% ${getTop(container, y, imgs.light)}`,
}}
/>
{imgs.dark && (
@@ -48,9 +62,10 @@ export function PageCoverImage({ imgs, y }: { imgs: Images; y: number }) {
sizes={imgs.dark.sizes}
fetchPriority="low"
alt="Page cover"
- className={tcls('h-full', 'w-full', 'object-cover', 'dark:inline', 'hidden')}
+ className={tcls('w-full', 'object-cover', 'dark:inline', 'hidden')}
style={{
- objectPosition: `50% ${objectPositionY}%`,
+ aspectRatio: `${PAGE_COVER_SIZE.width}/${PAGE_COVER_SIZE.height}`,
+ objectPosition: `50% ${getTop(container, y, imgs.dark)}`,
}}
/>
)}
diff --git a/packages/gitbook/src/components/PageBody/coverHeight.ts b/packages/gitbook/src/components/PageBody/coverHeight.ts
deleted file mode 100644
index e4f227770e..0000000000
--- a/packages/gitbook/src/components/PageBody/coverHeight.ts
+++ /dev/null
@@ -1,25 +0,0 @@
-import type { RevisionPageDocumentCover } from '@gitbook/api';
-
-export const DEFAULT_COVER_HEIGHT = 240;
-export const MIN_COVER_HEIGHT = 10;
-export const MAX_COVER_HEIGHT = 700;
-
-// Normalize and clamp the cover height between the minimum and maximum heights
-function clampCoverHeight(height: number | null | undefined): number {
- if (typeof height !== 'number' || Number.isNaN(height)) {
- return DEFAULT_COVER_HEIGHT;
- }
-
- return Math.min(MAX_COVER_HEIGHT, Math.max(MIN_COVER_HEIGHT, height));
-}
-
-export function getCoverHeight(
- cover: RevisionPageDocumentCover | null | undefined
-): number | undefined {
- // Cover (and thus height) is not defined
- if (!cover) {
- return undefined;
- }
-
- return clampCoverHeight((cover as RevisionPageDocumentCover).height ?? DEFAULT_COVER_HEIGHT);
-}
diff --git a/packages/gitbook/src/components/PageBody/index.ts b/packages/gitbook/src/components/PageBody/index.ts
index 74b91d6169..651c1bdb00 100644
--- a/packages/gitbook/src/components/PageBody/index.ts
+++ b/packages/gitbook/src/components/PageBody/index.ts
@@ -1,3 +1,2 @@
export * from './PageBody';
export * from './PageCover';
-export * from './useCoverPosition';
diff --git a/packages/gitbook/src/components/PageBody/useCoverPosition.ts b/packages/gitbook/src/components/PageBody/useCoverPosition.ts
deleted file mode 100644
index 7d749f48b0..0000000000
--- a/packages/gitbook/src/components/PageBody/useCoverPosition.ts
+++ /dev/null
@@ -1,109 +0,0 @@
-'use client';
-import { useLayoutEffect, useMemo, useRef, useState } from 'react';
-import { useResizeObserver } from 'usehooks-ts';
-
-interface ImageSize {
- width: number;
- height: number;
-}
-
-interface ImageAttributes {
- src: string;
- srcSet?: string;
- sizes?: string;
- width?: number;
- height?: number;
- size?: ImageSize;
-}
-
-interface Images {
- light: ImageAttributes;
- dark?: ImageAttributes;
-}
-
-/**
- * Hook to calculate the object position Y percentage for a cover image
- * based on the y offset, image dimensions, and container dimensions.
- */
-export function useCoverPosition(imgs: Images, y: number) {
- const containerRef = useRef(null);
- const [loadedDimensions, setLoadedDimensions] = useState(null);
- const [isLoading, setIsLoading] = useState(!imgs.light.size && !imgs.dark?.size);
-
- const container = useResizeObserver({
- // @ts-expect-error wrong types
- ref: containerRef,
- });
-
- // Load original image dimensions if not provided in `imgs`
- useLayoutEffect(() => {
- // Check if we have dimensions from either light or dark image
- const hasDimensions = imgs.light.size || imgs.dark?.size;
-
- if (hasDimensions) {
- return; // Already have dimensions
- }
-
- setIsLoading(true);
-
- // Load the original image (using src, not srcSet) to get true dimensions
- // Use dark image if available, otherwise fall back to light
- const imageToLoad = imgs.dark || imgs.light;
- const img = new Image();
- img.onload = () => {
- setLoadedDimensions({
- width: img.naturalWidth,
- height: img.naturalHeight,
- });
- setIsLoading(false);
- };
- img.onerror = () => {
- // If image fails to load, use a fallback
- setIsLoading(false);
- };
- img.src = imageToLoad.src;
- }, [imgs.light, imgs.dark]);
-
- // Use provided dimensions or fall back to loaded dimensions
- // Check light first, then dark, then loaded dimensions
- const imageDimensions = imgs.light.size ?? imgs.dark?.size ?? loadedDimensions;
-
- // Calculate ratio and dimensions similar to useCoverPosition hook
- const ratio =
- imageDimensions && container.height && container.width
- ? Math.max(
- container.width / imageDimensions.width,
- container.height / imageDimensions.height
- )
- : 1;
- const safeRatio = ratio || 1;
-
- const scaledHeight =
- imageDimensions && container.height ? imageDimensions.height * safeRatio : null;
- const maxOffset =
- scaledHeight && container.height
- ? Math.max(0, (scaledHeight - container.height) / 2 / safeRatio)
- : 0;
-
- // Parse the position between the allowed min/max
- const objectPositionY = useMemo(() => {
- if (!container.height || !imageDimensions) {
- return 50;
- }
-
- const scaled = imageDimensions.height * safeRatio;
- if (scaled <= container.height || maxOffset === 0) {
- return 50;
- }
-
- const clampedOffset = Math.max(-maxOffset, Math.min(maxOffset, y));
- const relative = (maxOffset - clampedOffset) / (2 * maxOffset);
- return relative * 100;
- }, [container.height, imageDimensions, maxOffset, safeRatio, y]);
-
- return {
- containerRef,
- objectPositionY,
- isLoading: !imageDimensions || isLoading,
- };
-}
From 47aefb747501cda086db2cefab36b09e2888a1cb Mon Sep 17 00:00:00 2001
From: Viktor Renkema
Date: Thu, 30 Oct 2025 10:10:42 +0100
Subject: [PATCH 2/2] Disable docs.gradient.network as theyre offline
---
packages/gitbook/e2e/customers.spec.ts | 10 +++++-----
1 file changed, 5 insertions(+), 5 deletions(-)
diff --git a/packages/gitbook/e2e/customers.spec.ts b/packages/gitbook/e2e/customers.spec.ts
index 3d79d09848..f0e18037b0 100644
--- a/packages/gitbook/e2e/customers.spec.ts
+++ b/packages/gitbook/e2e/customers.spec.ts
@@ -112,11 +112,11 @@ const testCases: TestsCase[] = [
contentBaseURL: 'https://adiblar.gitbook.io',
tests: [{ name: 'Home', url: '/' }],
},
- {
- name: 'docs.gradient.network',
- contentBaseURL: 'https://docs.gradient.network',
- tests: [{ name: 'Home', url: '/' }],
- },
+ // {
+ // name: 'docs.gradient.network',
+ // contentBaseURL: 'https://docs.gradient.network',
+ // tests: [{ name: 'Home', url: '/' }],
+ // },
// {
// name: 'mygate-network.gitbook.io',
// contentBaseURL: 'https://mygate-network.gitbook.io',