NextJS에서 Shadcn Select, Dialog 컴포넌트 사용 시 페이지 구조 깨짐 버그 해결법

Lenny·2025년 5월 22일

증상

요랬다가? Select를 열면?

이런식으로 페이지 구조가 깨지는 현상이 나타나는 버그(?) 가 있습니다.

마찬가지로 Dialog를 열면? 아래와 같이 페이지 구조가 깨집니다.

위 이미지들과 같이, body 아래에 렌더링 되는 요소들이 위로 이동하는 현상이 있어요.
Navigation 컴포넌트의 경우 Fixed 라서 고정되어 있지만요.

해결방법

저의 경우 원인은 body에 padding 속성을 넣어줬던것이 문제였습니다.

layout.tsx

"use client";

import "./globals.css";
import Navigation from "@/components/layout/navigation";
import { cn } from "@/lib/utils";
import { ThemeProvider } from "next-themes";
import { usePathname } from "next/navigation";

export default function RootLayout({
  children,
}: Readonly<{
  children: React.ReactNode;
}>) {
  const pathname = usePathname();
  const isAuthPage = pathname.startsWith("/auth");

  return (
    <html lang='en' suppressHydrationWarning>
      <body className={cn("pt-28", isAuthPage && "pt-0")}>
        <ThemeProvider attribute='class' defaultTheme='light'>
          {!isAuthPage && <Navigation />}
          {children}
        </ThemeProvider>
      </body>
    </html>
  );
}

Navigation의 높이만큼, padding-top을 주고있었어요.

다음과 같이 수정함으로써 위 이상현상을 해결할 수 있었습니다.

"use client";

import "./globals.css";
import Navigation from "@/components/layout/navigation";
import { cn } from "@/lib/utils";
import { ThemeProvider } from "next-themes";
import { usePathname } from "next/navigation";

export default function RootLayout({
  children,
}: Readonly<{
  children: React.ReactNode;
}>) {
  const pathname = usePathname();
  const isAuthPage = pathname.startsWith("/auth");

  return (
    <html lang='en' suppressHydrationWarning>
      <body>
        <div className={cn("pt-28", isAuthPage && "pt-0")}>
          <ThemeProvider attribute='class' defaultTheme='light'>
            {!isAuthPage && <Navigation />}
            {children}
          </ThemeProvider>
        </div>
      </body>
    </html>
  );
}

body에 바로 스타일을 주는게 아닌, div로 한번 더 감싸고 거기에 동일한 스타일을 넣어주니 문제가 해결되었습니다.

왜 이런 원인이 발생할까?

나도 몰루?

(제 추측으로는 Select나 Dialog를 열었을 때 렌더링되는 요소들, body 태그에 부여되는 속성과 관련이 있는것같아염.
그래서 body에 style을 바로 주게되면 해당 속성들과 충돌을 일으키면서 저의 padding-top 속성이 덮쓰 당해버리는것 같습니다?)

profile
🧑‍💻

0개의 댓글