Kliping
KlipingBerandaDokumentasiKomponenBlocksVariasiTemplateDice UIHooks
Memulai
  • Pengenalan
  • Instalasi
  • Kredit
State
  • useBoolean
  • useControllableValue
  • useCounter
  • useDebounce
  • useResetState
  • useThrottle
  • useToggle
Lanjutan
  • useCreation
  • useCustomCompareEffect
  • useLatest
  • useLockFn
  • useMemoizedFn
  • usePrevious
Siklus Hidup
  • useDebounceEffect
  • useDebounceFn
  • useDeepCompareEffect
  • useDeepCompareLayoutEffect
  • useEffectEvent
  • useEffectWithTarget
  • useInterval
  • useIsHydrated
  • useIsomorphicLayoutEffect
  • useMount
  • useThrottleEffect
  • useThrottleFn
  • useTimeout
  • useUnmount
  • useUpdate
  • useUpdateEffect
Peramban
  • useActiveElement
  • useBattery
  • useClickAnyWhere
  • useClickAway
  • useClipboard
  • useDocumentVisibility
  • useElementSize
  • useEventListener
  • useFps
  • useFullscreen
  • useHash
  • useHover
  • useInViewport
  • useIsMatchMedia
  • useIsOnline
  • useMouse
  • useNetwork
  • useOs
  • useScrollLock
  • useTextSelection
  • useTitle
Pengembangan
  • useWhyDidYouUpdate
Paket Luar
  • useMcp
  • useQuery
  • useStickToBottom
  • useSwr
Pustaka
  • isBrowser
  • createContext
  • bacaElemen
  • saatTerpasang

useTitle

SebelumnyaBerikutnya

Judul halaman, yang bisa dibaca dan ditulis.

Lihat tab peramban Anda — judulnya ikut berubah saat mengetik.

observe menyalakan pengamatan terhadap perubahan dari luar — kode lain, ekstensi, atau router yang menyetelnya sendiri. Mati secara bawaan, sama seperti sumbernya: satu MutationObserver di <head> bukan biaya yang pantas dibayar setiap halaman kalau tidak ada yang benar-benar membutuhkannya.

Judul yang ditulis sendiri diingat, supaya pengamatnya tidak menganggap tulisan sendiri sebagai perubahan dari luar lalu memantulkannya kembali.

Pemasangan ​

npx shadcn-vue@latest add @kliping/use-title

Perlu @kliping terdaftar di components.json project Anda. Lihat cara menyiapkannya.

Ikut terpasang sendiri: is-browser, saat-terpasang.

Salin dulu is-browser, saat-terpasang — masing-masing memuat sumbernya di halamannya sendiri — lalu tempel berkas ini.

ts
import { getCurrentScope, onScopeDispose, ref, toValue, watch } from 'vue'
import type { MaybeRefOrGetter, Ref } from 'vue'
import { isBrowser } from '@/lib/is-browser'
import { saatTerpasang } from '@/lib/saat-terpasang'

export interface UseTitleOptions {
  /** Ikuti perubahan judul yang datang dari luar. Bawaan: false. */
  observe?: boolean
  /** Pola judul akhir. `%s` diganti judulnya, atau berikan fungsi. */
  titleTemplate?: string | ((judul: string) => string)
}

function buatPola(pola?: string | ((judul: string) => string)) {
  if (typeof pola === 'function')
    return pola
  if (typeof pola === 'string' && pola.includes('%s'))
    return (judul: string) => pola.replaceAll('%s', judul)
  return (judul: string) => judul
}

export function useTitle(
  newTitle?: MaybeRefOrGetter<string | null | undefined>,
  options: UseTitleOptions = {},
) {
  const { observe = false, titleTemplate } = options
  const format = buatPola(titleTemplate)

  const judul = ref(
    toValue(newTitle) ?? (isBrowser ? document.title : ''),
  ) as Ref<string>

  // Judul terakhir yang ditulis dari sini. Pengamat memakainya untuk
  // membedakan tulisan sendiri dari perubahan yang datang dari luar.
  let ditulisSendiri: string | null = null

  watch(
    () => toValue(newTitle),
    (baru) => {
      if (baru != null && baru !== judul.value)
        judul.value = baru
    },
  )

  watch(
    judul,
    (baru) => {
      if (!isBrowser)
        return
      const akhir = format(baru)
      ditulisSendiri = akhir
      if (document.title !== akhir)
        document.title = akhir
    },
    { immediate: true },
  )

  let pengamat: MutationObserver | undefined

  saatTerpasang(() => {
    if (!observe || typeof MutationObserver === 'undefined')
      return

    const sasaran = document.head ?? document.documentElement
    if (!sasaran)
      return

    pengamat = new MutationObserver(() => {
      const kini = document.title
      if (ditulisSendiri === kini || judul.value === kini)
        return
      judul.value = kini
    })

    pengamat.observe(sasaran, { childList: true, subtree: true, characterData: true })
  })

  if (getCurrentScope())
    onScopeDispose(() => pengamat?.disconnect())

  return judul
}

API ​

ts
export interface UseTitleOptions {
  /** Ikuti perubahan judul yang datang dari luar. Bawaan: false. */
  observe?: boolean
  /** Pola judul akhir. `%s` diganti judulnya, atau berikan fungsi. */
  titleTemplate?: string | ((judul: string) => string)
}

export function useTitle(
  newTitle?: MaybeRefOrGetter<string | null | undefined>,
  options: UseTitleOptions = {},
)
useTextSelectionuseWhyDidYouUpdate

Di halaman ini

PemasanganAPI
Dirilis di bawah lisensi MIT. Ditulis ulang untuk Vue dari shadcn-vue, shadcn-ui-blocks, dan shadcn-hooks. Hak cipta © 2026 Kliping