Lang x Lang

useSelectedLayoutSegment

useSelectedLayoutSegmentは、呼び出し元の Layout の1 つ下の階層のアクティブな route セグメントを読み取ることができるClient Componentの hook です。

layout の親としてのタブなどのナビゲーション UI に便利であり、アクティブな子セグメントに応じて style が変わります。

app/example-client-component.tsx
'use client'

import { useSelectedLayoutSegment } from 'next/navigation'

export default function ExampleClientComponent() {
  const segment = useSelectedLayoutSegment()

  return <p>Active segment: {segment}</p>
}
app/example-client-component.js
'use client'

import { useSelectedLayoutSegment } from 'next/navigation'

export default function ExampleClientComponent() {
  const segment = useSelectedLayoutSegment()

  return <p>Active segment: {segment}</p>
}

Good to know:

  • useSelectedLayoutSegmentClient Componentの hook であり、レイアウトはServer Componentsが default ですので、通常、useSelectedLayoutSegmentは、 Layout にインポートされた Client Component を介して呼び出されます。
  • useSelectedLayoutSegmentは一つ下のレベルのセグメントのみを返します。すべてのアクティブなセグメントを返すには、useSelectedLayoutSegmentsをご覧ください。

Parameters

const segment = useSelectedLayoutSegment(parallelRoutesKey?: string)

useSelectedLayoutSegment はオプションで parallelRoutesKey を受け付けます。これにより、そのスロット内のアクティブな route セグメントを読み取ることができます。

Returns

useSelectedLayoutSegmentはアクティブなセグメントの string を返すか、存在しない場合はnullを返します。

たとえば、以下の Layout と URL が与えられた場合、返されるセグメントは以下のようになります:

Layout訪問した URL返されたセグメント
app/layout.js/null
app/layout.js/dashboard'dashboard'
app/dashboard/layout.js/dashboardnull
app/dashboard/layout.js/dashboard/settings'settings'
app/dashboard/layout.js/dashboard/analytics'analytics'
app/dashboard/layout.js/dashboard/analytics/monthly'analytics'

Examples

useSelectedLayoutSegmentを使用して、アクティブな link component を作成し、アクティブなセグメントに応じて style が変化することができます。例えば、ブログのサイドバーにある注目の投稿リスト:

app/blog/blog-nav-link.tsx
'use client'

import Link from 'next/link'
import { useSelectedLayoutSegment } from 'next/navigation'

// This *client* component will be imported into a blog layout
export default function BlogNavLink({
  slug,
  children,
}: {
  slug: string
  children: React.ReactNode
}) {
  // Navigating to `/blog/hello-world` will return 'hello-world'
  // for the selected layout segment
  const segment = useSelectedLayoutSegment()
  const isActive = slug === segment

  return (
    <Link
      href={`/blog/${slug}`}
      // Change style depending on whether the link is active
      style={{ fontWeight: isActive ? 'bold' : 'normal' }}
    >
      {children}
    </Link>
  )
}
app/blog/blog-nav-link.js
'use client'

import Link from 'next/link'
import { useSelectedLayoutSegment } from 'next/navigation'

// This *client* component will be imported into a blog layout
export default function BlogNavLink({ slug, children }) {
  // Navigating to `/blog/hello-world` will return 'hello-world'
  // for the selected layout segment
  const segment = useSelectedLayoutSegment()
  const isActive = slug === segment

  return (
    <Link
      href={`/blog/${slug}`}
      // Change style depending on whether the link is active
      style={{ fontWeight: isActive ? 'bold' : 'normal' }}
    >
      {children}
    </Link>
  )
}
app/blog/layout.tsx
// Import the Client Component into a parent Layout (Server Component)
import { BlogNavLink } from './blog-nav-link'
import getFeaturedPosts from './get-featured-posts'

export default async function Layout({
  children,
}: {
  children: React.ReactNode
}) {
  const featuredPosts = await getFeaturedPosts()
  return (
    <div>
      {featuredPosts.map((post) => (
        <div key={post.id}>
          <BlogNavLink slug={post.slug}>{post.title}</BlogNavLink>
        </div>
      ))}
      <div>{children}</div>
    </div>
  )
}
app/blog/layout.js
// Import the Client Component into a parent Layout (Server Component)
import { BlogNavLink } from './blog-nav-link'
import getFeaturedPosts from './get-featured-posts'

export default async function Layout({ children }) {
  const featuredPosts = await getFeaturedPosts()
  return (
    <div>
      {featuredPosts.map((post) => (
        <div key={post.id}>
          <BlogNavLink slug={post.slug}>{post.title}</BlogNavLink>
        </div>
      ))}
      <div>{children}</div>
    </div>
  )
}

Version History

VersionChanges
v13.0.0useSelectedLayoutSegmentが導入されました。

当社サイトでは、Cookie を使用しています。各規約をご確認の上ご利用ください:
Cookie Policy, Privacy Policy および Terms of Use