上下文

Qwik 提供了一個 context API,它解決了 props drilling 的問題,並且與 React 的函數式 useContext() 非常相似。事實上,Qwik 的 context API 是將數據傳遞給不同組件的最有效方式,它可以減少開銷、生成更少的代碼,並允許 Qwik 更有效地對未使用的數據進行 樹搖

Qwik 的 context API 由 3 個方法組成,可以從 @builder.io/qwik 中導入

import { type Signal, component$, useSignal } from '@builder.io/qwik';
import {
  useContext,
  useContextProvider,
  createContextId,
} from '@builder.io/qwik';
 
export const ThemeContext = createContextId<Signal<string>>(
  'docs.theme-context'
);
 
export default component$(() => {
  const theme = useSignal('dark');
  useContextProvider(ThemeContext, theme);
  return (
    <>
      <button
        onClick$={() =>
          (theme.value = theme.value == 'dark' ? 'light' : 'dark')
        }
      >
        Flip
      </button>
      <Child />
    </>
  );
});
 
const Child = component$(() => {
  const theme = useContext(ThemeContext);
  return <div>Theme is {theme.value}</div>;
});

在上面的例子中,創建了一個名為 docs.theme-contextContextId,並使用它為 default 組件提供一個 useSignalChild 組件使用 useContext 方法獲取 useSignal 並渲染其值。

createContextId()

此方法用於創建新的 ContextId

export interface GenericType {
  ...
}
 
export const QwikCityContext = createContextId<GenericType>(name: string): ContextId<GenericType>;

參數

  • name: 是一個賦予 createContextId 的唯一字符串,作為上下文的標識符。這將避免在存在多個上下文時發生衝突。建議使用 io.builder.qwik.city 之類的命名約定。

回傳值

請注意,createContextId() 返回的值不包含任何狀態,它是一個不可變的 ID 對象,即 { id: 'io.builder.qwik.city' }。它僅用於描述上下文的的名稱和類型,例如地址或標識符。由於它不包含任何狀態,因此可以將其初始化為單例並從共享模組中匯出。

useContextProvider()

此方法用於使用 ContextId 作為上下文的關鍵標識符,為特定組件及其後代創建上下文。

src/components/Parent.tsx
import { component$, useStore, useContextProvider } from '@builder.io/qwik';
 
export const Parent = component$(() => {
 
  const qwikCityObject = useStore<GenericType>({
    ...
  });
 
  useContextProvider(QwikCityContext, qwikCityObject);
  useContextProvider(PlainArrayContext, [1, 2, 3])
  useContextProvider(AppNameContext, "My Qwik App")
 
  return (
    <Children />
  );
});

參數

  • ContextId:必須提供先前創建的上下文,作為第二個參數提供的數據的標識符。

  • data:您可以提供任何數據類型,例如 Qwik 的 useSignal、useStore、數組或對象。

注意事項

  • 提供的值不會在整個渲染樹中全局可用,而僅對樹中的後代組件可用。
  • 如果在服務器端渲染 (SSR) 期間未使用上下文,則不會對其進行序列化。如果您需要在客戶端上使用上下文,即使在 SSR 期間未使用它,您也應該在父組件中調用 useContext()。這將強制對其進行序列化。

useContext()

此方法用於獲取由父組件提供Context 的值。

src/components/Children.tsx
import { component$, useContext } from '@builder.io/qwik';
 
export const Children = component$(() => {
  const qwikCityObject = useContext(QwikCityContext);
  const plainArray = useContext(PlainArrayContext);
  const appName = useContext(AppNameContext);
 
  return (
    <div>Child components can use any of the provided values, such as {appName}</div>
  );
});

貢獻者

感謝所有幫助改進此文檔的貢獻者!

  • manucorporat
  • RATIU5
  • nnelgxorz
  • adamdbradley
  • the-r3aper7
  • cunzaizhuyi
  • forresst
  • kerbelp
  • shairez
  • mhevery
  • AnthonyPAlicea
  • steve8708
  • mrhoodz
  • Jemsco