[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill:01M71TDMPW7FJV71VPS09JSXXM":3,"skill-same:01M71TDMPW7FJV71VPS09JSXXM":59},{"skillNo":4,"name":5,"nameZh":6,"description":7,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":16,"categories":17,"keywords":18,"publishedAt":31,"linkOnly":32,"markdownContent":33,"markdownBody":34,"frontMatter":35,"refName":37,"commitSha":38,"skillDirectory":39,"forksCount":40,"repositoryHtmlUrl":41,"repositoryHomepageUrl":6,"ownerHtmlUrl":42,"ownerBlogUrl":6,"ownerDescription":43,"updatedAt":44,"install":45,"resources":58},"01M71TDMPW7FJV71VPS09JSXXM","use-dom",null,"Use Expo DOM components to run web code in a webview on native and as-is on web. Migrate web code to native incrementally.","vitalikpestov\u002FSkills-Catalog","vitalikpestov","https:\u002F\u002Favatars.githubusercontent.com\u002Fu\u002F13882997?v=4","01M71N4QG0CWRXX4R24JQZXDDQ","Vitalik Pestov","01M71N4QGMSYRW607DDSE0CQMM",2,"MIT","https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog\u002Fblob\u002Fmain\u002F_Mobile-Dev\u002Ffrom-reddit-mobile-apps\u002Fexpo-skills\u002Fplugins\u002Fexpo\u002Fskills\u002Fuse-dom\u002FSKILL.md",[],[19,20,21,22,23,24,25,26,27,28,29,30],"use","use dom","dom","expo dom","as","migrate","code","components","web","native","run","expo","2026-11-10 13:02:02",false,"---\nname: use-dom\ndescription: Use Expo DOM components to run web code in a webview on native and as-is on web. Migrate web code to native incrementally.\nversion: 1.0.0\nlicense: MIT\n---\n\n## What are DOM Components?\n\nDOM components allow web code to run verbatim in a webview on native platforms while rendering as-is on web. This enables using web-only libraries like `recharts`, `react-syntax-highlighter`, or any React web library in your Expo app without modification.\n\n## When to Use DOM Components\n\nUse DOM components when you need:\n\n- **Web-only libraries** — Charts (recharts, chart.js), syntax highlighters, rich text editors, or any library that depends on DOM APIs\n- **Migrating web code** — Bring existing React web components to native without rewriting\n- **Complex HTML\u002FCSS layouts** — When CSS features aren't available in React Native\n- **iframes or embeds** — Embedding external content that requires a browser context\n- **Canvas or WebGL** — Web graphics APIs not available natively\n\n## When NOT to Use DOM Components\n\nAvoid DOM components when:\n\n- **Native performance is critical** — Webviews add overhead\n- **Simple UI** — React Native components are more efficient for basic layouts\n- **Deep native integration** — Use local modules instead for native APIs\n- **Layout routes** — `_layout` files cannot be DOM components\n\n## Basic DOM Component\n\nCreate a new file with the `'use dom';` directive at the top:\n\n```tsx\n\u002F\u002F components\u002FWebChart.tsx\n\"use dom\";\n\nexport default function WebChart({\n  data,\n}: {\n  data: number[];\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  return (\n    \u003Cdiv style={{ padding: 20 }}>\n      \u003Ch2>Chart Data\u003C\u002Fh2>\n      \u003Cul>\n        {data.map((value, i) => (\n          \u003Cli key={i}>{value}\u003C\u002Fli>\n        ))}\n      \u003C\u002Ful>\n    \u003C\u002Fdiv>\n  );\n}\n```\n\n## Rules for DOM Components\n\n1. **Must have `'use dom';` directive** at the top of the file\n2. **Single default export** — One React component per file\n3. **Own file** — Cannot be defined inline or combined with native components\n4. **Serializable props only** — Strings, numbers, booleans, arrays, plain objects\n5. **Include CSS in the component file** — DOM components run in isolated context\n\n## The `dom` Prop\n\nEvery DOM component receives a special `dom` prop for webview configuration. Always type it in your props:\n\n```tsx\n\"use dom\";\n\ninterface Props {\n  content: string;\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}\n\nexport default function MyComponent({ content }: Props) {\n  return \u003Cdiv>{content}\u003C\u002Fdiv>;\n}\n```\n\n### Common `dom` Prop Options\n\n```tsx\n\u002F\u002F Disable body scrolling\n\u003CDOMComponent dom={{ scrollEnabled: false }} \u002F>\n\n\u002F\u002F Flow under the notch (disable safe area insets)\n\u003CDOMComponent dom={{ contentInsetAdjustmentBehavior: \"never\" }} \u002F>\n\n\u002F\u002F Control size manually\n\u003CDOMComponent dom={{ style: { width: 300, height: 400 } }} \u002F>\n\n\u002F\u002F Combine options\n\u003CDOMComponent\n  dom={{\n    scrollEnabled: false,\n    contentInsetAdjustmentBehavior: \"never\",\n    style: { width: '100%', height: 500 }\n  }}\n\u002F>\n```\n\n## Exposing Native Actions to the Webview\n\nPass async functions as props to expose native functionality to the DOM component:\n\n```tsx\n\u002F\u002F app\u002Findex.tsx (native)\nimport { Alert } from \"react-native\";\nimport DOMComponent from \"@\u002Fcomponents\u002Fdom-component\";\n\nexport default function Screen() {\n  return (\n    \u003CDOMComponent\n      showAlert={async (message: string) => {\n        Alert.alert(\"From Web\", message);\n      }}\n      saveData={async (data: { name: string; value: number }) => {\n        \u002F\u002F Save to native storage, database, etc.\n        console.log(\"Saving:\", data);\n        return { success: true };\n      }}\n    \u002F>\n  );\n}\n```\n\n```tsx\n\u002F\u002F components\u002Fdom-component.tsx\n\"use dom\";\n\ninterface Props {\n  showAlert: (message: string) => Promise\u003Cvoid>;\n  saveData: (data: {\n    name: string;\n    value: number;\n  }) => Promise\u003C{ success: boolean }>;\n  dom?: import(\"expo\u002Fdom\").DOMProps;\n}\n\nexport default function DOMComponent({ showAlert, saveData }: Props) {\n  const handleClick = async () => {\n    await showAlert(\"Hello from the webview!\");\n    const result = await saveData({ name: \"test\", value: 42 });\n    console.log(\"Save result:\", result);\n  };\n\n  return \u003Cbutton onClick={handleClick}>Trigger Native Action\u003C\u002Fbutton>;\n}\n```\n\n## Using Web Libraries\n\nDOM components can use any web library:\n\n```tsx\n\u002F\u002F components\u002Fsyntax-highlight.tsx\n\"use dom\";\n\nimport SyntaxHighlighter from \"react-syntax-highlighter\";\nimport { docco } from \"react-syntax-highlighter\u002Fdist\u002Fesm\u002Fstyles\u002Fhljs\";\n\ninterface Props {\n  code: string;\n  language: string;\n  dom?: import(\"expo\u002Fdom\").DOMProps;\n}\n\nexport default function SyntaxHighlight({ code, language }: Props) {\n  return (\n    \u003CSyntaxHighlighter language={language} style={docco}>\n      {code}\n    \u003C\u002FSyntaxHighlighter>\n  );\n}\n```\n\n```tsx\n\u002F\u002F components\u002Fchart.tsx\n\"use dom\";\n\nimport {\n  LineChart,\n  Line,\n  XAxis,\n  YAxis,\n  CartesianGrid,\n  Tooltip,\n} from \"recharts\";\n\ninterface Props {\n  data: Array\u003C{ name: string; value: number }>;\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}\n\nexport default function Chart({ data }: Props) {\n  return (\n    \u003CLineChart width={400} height={300} data={data}>\n      \u003CCartesianGrid strokeDasharray=\"3 3\" \u002F>\n      \u003CXAxis dataKey=\"name\" \u002F>\n      \u003CYAxis \u002F>\n      \u003CTooltip \u002F>\n      \u003CLine type=\"monotone\" dataKey=\"value\" stroke=\"#8884d8\" \u002F>\n    \u003C\u002FLineChart>\n  );\n}\n```\n\n## CSS in DOM Components\n\nCSS imports must be in the DOM component file since they run in isolated context:\n\n```tsx\n\u002F\u002F components\u002Fstyled-component.tsx\n\"use dom\";\n\nimport \"@\u002Fstyles.css\"; \u002F\u002F CSS file in same directory\n\nexport default function StyledComponent({\n  dom,\n}: {\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  return (\n    \u003Cdiv className=\"container\">\n      \u003Ch1 className=\"title\">Styled Content\u003C\u002Fh1>\n    \u003C\u002Fdiv>\n  );\n}\n```\n\nOr use inline styles \u002F CSS-in-JS:\n\n```tsx\n\"use dom\";\n\nconst styles = {\n  container: {\n    padding: 20,\n    backgroundColor: \"#f0f0f0\",\n  },\n  title: {\n    fontSize: 24,\n    color: \"#333\",\n  },\n};\n\nexport default function StyledComponent({\n  dom,\n}: {\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  return (\n    \u003Cdiv style={styles.container}>\n      \u003Ch1 style={styles.title}>Styled Content\u003C\u002Fh1>\n    \u003C\u002Fdiv>\n  );\n}\n```\n\n## Expo Router in DOM Components\n\nThe expo-router `\u003CLink \u002F>` component and router API work inside DOM components:\n\n```tsx\n\"use dom\";\n\nimport { Link, useRouter } from \"expo-router\";\n\nexport default function Navigation({\n  dom,\n}: {\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  const router = useRouter();\n\n  return (\n    \u003Cnav>\n      \u003CLink href=\"\u002Fabout\">About\u003C\u002FLink>\n      \u003Cbutton onClick={() => router.push(\"\u002Fsettings\")}>Settings\u003C\u002Fbutton>\n    \u003C\u002Fnav>\n  );\n}\n```\n\n### Router APIs That Require Props\n\nThese hooks don't work directly in DOM components because they need synchronous access to native routing state:\n\n- `useLocalSearchParams()`\n- `useGlobalSearchParams()`\n- `usePathname()`\n- `useSegments()`\n- `useRootNavigation()`\n- `useRootNavigationState()`\n\n**Solution:** Read these values in the native parent and pass as props:\n\n```tsx\n\u002F\u002F app\u002F[id].tsx (native)\nimport { useLocalSearchParams, usePathname } from \"expo-router\";\nimport DOMComponent from \"@\u002Fcomponents\u002Fdom-component\";\n\nexport default function Screen() {\n  const { id } = useLocalSearchParams();\n  const pathname = usePathname();\n\n  return \u003CDOMComponent id={id as string} pathname={pathname} \u002F>;\n}\n```\n\n```tsx\n\u002F\u002F components\u002Fdom-component.tsx\n\"use dom\";\n\ninterface Props {\n  id: string;\n  pathname: string;\n  dom?: import(\"expo\u002Fdom\").DOMProps;\n}\n\nexport default function DOMComponent({ id, pathname }: Props) {\n  return (\n    \u003Cdiv>\n      \u003Cp>Current ID: {id}\u003C\u002Fp>\n      \u003Cp>Current Path: {pathname}\u003C\u002Fp>\n    \u003C\u002Fdiv>\n  );\n}\n```\n\n## Detecting DOM Environment\n\nCheck if code is running in a DOM component:\n\n```tsx\n\"use dom\";\n\nimport { IS_DOM } from \"expo\u002Fdom\";\n\nexport default function Component({\n  dom,\n}: {\n  dom?: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  return \u003Cdiv>{IS_DOM ? \"Running in DOM component\" : \"Running natively\"}\u003C\u002Fdiv>;\n}\n```\n\n## Assets\n\nPrefer requiring assets instead of using the public directory:\n\n```tsx\n\"use dom\";\n\n\u002F\u002F Good - bundled with the component\nconst logo = require(\"..\u002Fassets\u002Flogo.png\");\n\nexport default function Component({\n  dom,\n}: {\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  return \u003Cimg src={logo} alt=\"Logo\" \u002F>;\n}\n```\n\n## Usage from Native Components\n\nImport and use DOM components like regular components:\n\n```tsx\n\u002F\u002F app\u002Findex.tsx\nimport { View, Text } from \"react-native\";\nimport WebChart from \"@\u002Fcomponents\u002Fweb-chart\";\nimport CodeBlock from \"@\u002Fcomponents\u002Fcode-block\";\n\nexport default function HomeScreen() {\n  return (\n    \u003CView style={{ flex: 1 }}>\n      \u003CText>Native content above\u003C\u002FText>\n\n      \u003CWebChart data={[10, 20, 30, 40, 50]} dom={{ style: { height: 300 } }} \u002F>\n\n      \u003CCodeBlock\n        code=\"const x = 1;\"\n        language=\"javascript\"\n        dom={{ scrollEnabled: true }}\n      \u002F>\n\n      \u003CText>Native content below\u003C\u002FText>\n    \u003C\u002FView>\n  );\n}\n```\n\n## Platform Behavior\n\n| Platform | Behavior                            |\n| -------- | ----------------------------------- |\n| iOS      | Rendered in WKWebView               |\n| Android  | Rendered in WebView                 |\n| Web      | Rendered as-is (no webview wrapper) |\n\nOn web, the `dom` prop is ignored since no webview is needed.\n\n## Tips\n\n- DOM components hot reload during development\n- Keep DOM components focused — don't put entire screens in webviews\n- Use native components for navigation chrome, DOM components for specialized content\n- Test on all platforms — web rendering may differ slightly from native webviews\n- Large DOM components may impact performance — profile if needed\n- The webview has its own JavaScript context — cannot directly share state with native\n","## What are DOM Components?\n\nDOM components allow web code to run verbatim in a webview on native platforms while rendering as-is on web. This enables using web-only libraries like `recharts`, `react-syntax-highlighter`, or any React web library in your Expo app without modification.\n\n## When to Use DOM Components\n\nUse DOM components when you need:\n\n- **Web-only libraries** — Charts (recharts, chart.js), syntax highlighters, rich text editors, or any library that depends on DOM APIs\n- **Migrating web code** — Bring existing React web components to native without rewriting\n- **Complex HTML\u002FCSS layouts** — When CSS features aren't available in React Native\n- **iframes or embeds** — Embedding external content that requires a browser context\n- **Canvas or WebGL** — Web graphics APIs not available natively\n\n## When NOT to Use DOM Components\n\nAvoid DOM components when:\n\n- **Native performance is critical** — Webviews add overhead\n- **Simple UI** — React Native components are more efficient for basic layouts\n- **Deep native integration** — Use local modules instead for native APIs\n- **Layout routes** — `_layout` files cannot be DOM components\n\n## Basic DOM Component\n\nCreate a new file with the `'use dom';` directive at the top:\n\n```tsx\n\u002F\u002F components\u002FWebChart.tsx\n\"use dom\";\n\nexport default function WebChart({\n  data,\n}: {\n  data: number[];\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  return (\n    \u003Cdiv style={{ padding: 20 }}>\n      \u003Ch2>Chart Data\u003C\u002Fh2>\n      \u003Cul>\n        {data.map((value, i) => (\n          \u003Cli key={i}>{value}\u003C\u002Fli>\n        ))}\n      \u003C\u002Ful>\n    \u003C\u002Fdiv>\n  );\n}\n```\n\n## Rules for DOM Components\n\n1. **Must have `'use dom';` directive** at the top of the file\n2. **Single default export** — One React component per file\n3. **Own file** — Cannot be defined inline or combined with native components\n4. **Serializable props only** — Strings, numbers, booleans, arrays, plain objects\n5. **Include CSS in the component file** — DOM components run in isolated context\n\n## The `dom` Prop\n\nEvery DOM component receives a special `dom` prop for webview configuration. Always type it in your props:\n\n```tsx\n\"use dom\";\n\ninterface Props {\n  content: string;\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}\n\nexport default function MyComponent({ content }: Props) {\n  return \u003Cdiv>{content}\u003C\u002Fdiv>;\n}\n```\n\n### Common `dom` Prop Options\n\n```tsx\n\u002F\u002F Disable body scrolling\n\u003CDOMComponent dom={{ scrollEnabled: false }} \u002F>\n\n\u002F\u002F Flow under the notch (disable safe area insets)\n\u003CDOMComponent dom={{ contentInsetAdjustmentBehavior: \"never\" }} \u002F>\n\n\u002F\u002F Control size manually\n\u003CDOMComponent dom={{ style: { width: 300, height: 400 } }} \u002F>\n\n\u002F\u002F Combine options\n\u003CDOMComponent\n  dom={{\n    scrollEnabled: false,\n    contentInsetAdjustmentBehavior: \"never\",\n    style: { width: '100%', height: 500 }\n  }}\n\u002F>\n```\n\n## Exposing Native Actions to the Webview\n\nPass async functions as props to expose native functionality to the DOM component:\n\n```tsx\n\u002F\u002F app\u002Findex.tsx (native)\nimport { Alert } from \"react-native\";\nimport DOMComponent from \"@\u002Fcomponents\u002Fdom-component\";\n\nexport default function Screen() {\n  return (\n    \u003CDOMComponent\n      showAlert={async (message: string) => {\n        Alert.alert(\"From Web\", message);\n      }}\n      saveData={async (data: { name: string; value: number }) => {\n        \u002F\u002F Save to native storage, database, etc.\n        console.log(\"Saving:\", data);\n        return { success: true };\n      }}\n    \u002F>\n  );\n}\n```\n\n```tsx\n\u002F\u002F components\u002Fdom-component.tsx\n\"use dom\";\n\ninterface Props {\n  showAlert: (message: string) => Promise\u003Cvoid>;\n  saveData: (data: {\n    name: string;\n    value: number;\n  }) => Promise\u003C{ success: boolean }>;\n  dom?: import(\"expo\u002Fdom\").DOMProps;\n}\n\nexport default function DOMComponent({ showAlert, saveData }: Props) {\n  const handleClick = async () => {\n    await showAlert(\"Hello from the webview!\");\n    const result = await saveData({ name: \"test\", value: 42 });\n    console.log(\"Save result:\", result);\n  };\n\n  return \u003Cbutton onClick={handleClick}>Trigger Native Action\u003C\u002Fbutton>;\n}\n```\n\n## Using Web Libraries\n\nDOM components can use any web library:\n\n```tsx\n\u002F\u002F components\u002Fsyntax-highlight.tsx\n\"use dom\";\n\nimport SyntaxHighlighter from \"react-syntax-highlighter\";\nimport { docco } from \"react-syntax-highlighter\u002Fdist\u002Fesm\u002Fstyles\u002Fhljs\";\n\ninterface Props {\n  code: string;\n  language: string;\n  dom?: import(\"expo\u002Fdom\").DOMProps;\n}\n\nexport default function SyntaxHighlight({ code, language }: Props) {\n  return (\n    \u003CSyntaxHighlighter language={language} style={docco}>\n      {code}\n    \u003C\u002FSyntaxHighlighter>\n  );\n}\n```\n\n```tsx\n\u002F\u002F components\u002Fchart.tsx\n\"use dom\";\n\nimport {\n  LineChart,\n  Line,\n  XAxis,\n  YAxis,\n  CartesianGrid,\n  Tooltip,\n} from \"recharts\";\n\ninterface Props {\n  data: Array\u003C{ name: string; value: number }>;\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}\n\nexport default function Chart({ data }: Props) {\n  return (\n    \u003CLineChart width={400} height={300} data={data}>\n      \u003CCartesianGrid strokeDasharray=\"3 3\" \u002F>\n      \u003CXAxis dataKey=\"name\" \u002F>\n      \u003CYAxis \u002F>\n      \u003CTooltip \u002F>\n      \u003CLine type=\"monotone\" dataKey=\"value\" stroke=\"#8884d8\" \u002F>\n    \u003C\u002FLineChart>\n  );\n}\n```\n\n## CSS in DOM Components\n\nCSS imports must be in the DOM component file since they run in isolated context:\n\n```tsx\n\u002F\u002F components\u002Fstyled-component.tsx\n\"use dom\";\n\nimport \"@\u002Fstyles.css\"; \u002F\u002F CSS file in same directory\n\nexport default function StyledComponent({\n  dom,\n}: {\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  return (\n    \u003Cdiv className=\"container\">\n      \u003Ch1 className=\"title\">Styled Content\u003C\u002Fh1>\n    \u003C\u002Fdiv>\n  );\n}\n```\n\nOr use inline styles \u002F CSS-in-JS:\n\n```tsx\n\"use dom\";\n\nconst styles = {\n  container: {\n    padding: 20,\n    backgroundColor: \"#f0f0f0\",\n  },\n  title: {\n    fontSize: 24,\n    color: \"#333\",\n  },\n};\n\nexport default function StyledComponent({\n  dom,\n}: {\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  return (\n    \u003Cdiv style={styles.container}>\n      \u003Ch1 style={styles.title}>Styled Content\u003C\u002Fh1>\n    \u003C\u002Fdiv>\n  );\n}\n```\n\n## Expo Router in DOM Components\n\nThe expo-router `\u003CLink \u002F>` component and router API work inside DOM components:\n\n```tsx\n\"use dom\";\n\nimport { Link, useRouter } from \"expo-router\";\n\nexport default function Navigation({\n  dom,\n}: {\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  const router = useRouter();\n\n  return (\n    \u003Cnav>\n      \u003CLink href=\"\u002Fabout\">About\u003C\u002FLink>\n      \u003Cbutton onClick={() => router.push(\"\u002Fsettings\")}>Settings\u003C\u002Fbutton>\n    \u003C\u002Fnav>\n  );\n}\n```\n\n### Router APIs That Require Props\n\nThese hooks don't work directly in DOM components because they need synchronous access to native routing state:\n\n- `useLocalSearchParams()`\n- `useGlobalSearchParams()`\n- `usePathname()`\n- `useSegments()`\n- `useRootNavigation()`\n- `useRootNavigationState()`\n\n**Solution:** Read these values in the native parent and pass as props:\n\n```tsx\n\u002F\u002F app\u002F[id].tsx (native)\nimport { useLocalSearchParams, usePathname } from \"expo-router\";\nimport DOMComponent from \"@\u002Fcomponents\u002Fdom-component\";\n\nexport default function Screen() {\n  const { id } = useLocalSearchParams();\n  const pathname = usePathname();\n\n  return \u003CDOMComponent id={id as string} pathname={pathname} \u002F>;\n}\n```\n\n```tsx\n\u002F\u002F components\u002Fdom-component.tsx\n\"use dom\";\n\ninterface Props {\n  id: string;\n  pathname: string;\n  dom?: import(\"expo\u002Fdom\").DOMProps;\n}\n\nexport default function DOMComponent({ id, pathname }: Props) {\n  return (\n    \u003Cdiv>\n      \u003Cp>Current ID: {id}\u003C\u002Fp>\n      \u003Cp>Current Path: {pathname}\u003C\u002Fp>\n    \u003C\u002Fdiv>\n  );\n}\n```\n\n## Detecting DOM Environment\n\nCheck if code is running in a DOM component:\n\n```tsx\n\"use dom\";\n\nimport { IS_DOM } from \"expo\u002Fdom\";\n\nexport default function Component({\n  dom,\n}: {\n  dom?: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  return \u003Cdiv>{IS_DOM ? \"Running in DOM component\" : \"Running natively\"}\u003C\u002Fdiv>;\n}\n```\n\n## Assets\n\nPrefer requiring assets instead of using the public directory:\n\n```tsx\n\"use dom\";\n\n\u002F\u002F Good - bundled with the component\nconst logo = require(\"..\u002Fassets\u002Flogo.png\");\n\nexport default function Component({\n  dom,\n}: {\n  dom: import(\"expo\u002Fdom\").DOMProps;\n}) {\n  return \u003Cimg src={logo} alt=\"Logo\" \u002F>;\n}\n```\n\n## Usage from Native Components\n\nImport and use DOM components like regular components:\n\n```tsx\n\u002F\u002F app\u002Findex.tsx\nimport { View, Text } from \"react-native\";\nimport WebChart from \"@\u002Fcomponents\u002Fweb-chart\";\nimport CodeBlock from \"@\u002Fcomponents\u002Fcode-block\";\n\nexport default function HomeScreen() {\n  return (\n    \u003CView style={{ flex: 1 }}>\n      \u003CText>Native content above\u003C\u002FText>\n\n      \u003CWebChart data={[10, 20, 30, 40, 50]} dom={{ style: { height: 300 } }} \u002F>\n\n      \u003CCodeBlock\n        code=\"const x = 1;\"\n        language=\"javascript\"\n        dom={{ scrollEnabled: true }}\n      \u002F>\n\n      \u003CText>Native content below\u003C\u002FText>\n    \u003C\u002FView>\n  );\n}\n```\n\n## Platform Behavior\n\n| Platform | Behavior                            |\n| -------- | ----------------------------------- |\n| iOS      | Rendered in WKWebView               |\n| Android  | Rendered in WebView                 |\n| Web      | Rendered as-is (no webview wrapper) |\n\nOn web, the `dom` prop is ignored since no webview is needed.\n\n## Tips\n\n- DOM components hot reload during development\n- Keep DOM components focused — don't put entire screens in webviews\n- Use native components for navigation chrome, DOM components for specialized content\n- Test on all platforms — web rendering may differ slightly from native webviews\n- Large DOM components may impact performance — profile if needed\n- The webview has its own JavaScript context — cannot directly share state with native\n",{"name":5,"license":15,"version":36,"description":7},"1.0.0","main","fbfb242f793fdf040f3a1a6b100896c188c228c8","_Mobile-Dev\u002Ffrom-reddit-mobile-apps\u002Fexpo-skills\u002Fplugins\u002Fexpo\u002Fskills\u002Fuse-dom",1,"https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog","https:\u002F\u002Fgithub.com\u002Fvitalikpestov","Listing on crypto exchanges","2026-06-15 22:12:56",{"source":8,"skillName":5,"commands":46,"prompt":56,"zipAvailable":57},[47,50,53],{"tool":48,"command":49},"npx","npx skills add vitalikpestov\u002FSkills-Catalog --skill use-dom",{"tool":51,"command":52},"bunx","bunx skills add vitalikpestov\u002FSkills-Catalog --skill use-dom",{"tool":54,"command":55},"pnpm","pnpm dlx skills add vitalikpestov\u002FSkills-Catalog --skill use-dom","安装技能，技能地址：https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog\u002Fblob\u002Fmain\u002F_Mobile-Dev\u002Ffrom-reddit-mobile-apps\u002Fexpo-skills\u002Fplugins\u002Fexpo\u002Fskills\u002Fuse-dom\u002FSKILL.md",true,[],[60,103,128,145,168,201],{"skillNo":61,"name":62,"nameZh":6,"description":63,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":64,"categories":65,"keywords":82,"publishedAt":31},"01M71V1MC994P553631JZSWVYD","solana-dev","Use when user asks to \"build a Solana dapp\", \"write an Anchor program\", \"create a token\", \"debug Solana errors\", \"set up wallet connection\", \"test my Solana program\", \"deploy to devnet\", or \"explain Solana concepts\" (rent, accounts, PDAs, CPIs, etc.). End-to-end Solana development playbook covering wallet connection, Anchor\u002FPinocchio programs, Codama client generation, LiteSVM\u002FMollusk\u002FSurfpool testing, and security checklists. Integrates with the Solana MCP server for live documentation search. Prefers framework-kit (@solana\u002Fclient + @solana\u002Freact-hooks) for UI, wallet-standard-first connection (incl. ConnectorKit), @solana\u002Fkit for client\u002FRPC code, and @solana\u002Fweb3-compat for legacy boundaries.","https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog\u002Fblob\u002Fmain\u002F_Web3\u002Fsolana-dev\u002Fskill\u002FSKILL.md",[66,71,74,77],{"categoryNo":67,"categoryName":68,"taxonomyType":69,"taxonomyTypeDesc":70},"01JBSEEDCAT000000000000008","测试与质量","SCENARIO","使用场景",{"categoryNo":72,"categoryName":73,"taxonomyType":69,"taxonomyTypeDesc":70},"01JBSEEDCAT000000000000009","前端开发",{"categoryNo":75,"categoryName":76,"taxonomyType":69,"taxonomyTypeDesc":70},"01JBSEEDCAT000000000000023","Skill与智能体开发",{"categoryNo":78,"categoryName":79,"taxonomyType":80,"taxonomyTypeDesc":81},"01JBSEEDCAT000000000000030","开发工程师","PROFESSION","适用职业",[83,84,85,86,87,88,89,90,91,92,93,94,95,96,97,98,99,100,101,102],"dev","solana dev","solana","Wallet","search","testing","solana cli","kit","MCP","web3","react","create","server","write","playbook","live","security","ui","concepts","toolchain",{"skillNo":104,"name":105,"nameZh":6,"description":106,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":107,"categories":108,"keywords":109,"publishedAt":31},"01M71TYQPHE2YGKTT7DG9QCW3K","generating-trading-signals","Generate trading signals using technical indicators (RSI, MACD, Bollinger Bands, etc.).\nCombines multiple indicators into composite signals with confidence scores.\nUse when analyzing assets for trading opportunities or checking technical indicators.\nTrigger with phrases like \"get trading signals\", \"check indicators\", \"analyze for entry\",\n\"scan for opportunities\", \"generate buy\u002Fsell signals\", or \"technical analysis\".","https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog\u002Fblob\u002Fmain\u002F_Trading-Finance\u002Fgenerating-trading-signals\u002FSKILL.md",[],[110,111,112,113,114,115,116,117,118,119,120,121,19,122,123,124,25,125,126,127],"generating trading signals","signals","trading signals","trading","get","technical indicators","for","scan","rsi","trigger","python","technical","when","Bash","analysis","io","check","analyze",{"skillNo":129,"name":130,"nameZh":6,"description":131,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":132,"categories":133,"keywords":134,"publishedAt":31},"01M71TY4CR3GKGQ3M12X9WN95Y","prediction-monitor","Prediction Monitor - Auto-activating skill for ML Deployment.\nTriggers on: prediction monitor, prediction monitor\nPart of the ML Deployment skill category.","https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog\u002Fblob\u002Fmain\u002F_Trading-Finance\u002FAI Predictions\u002Fprediction-monitor\u002FSKILL.md",[],[135,136,137,116,138,139,96,140,141,142,143,144,123],"prediction","monitor","prediction monitor","deployment","read","edit","triggers","grep","auto","ml",{"skillNo":146,"name":147,"nameZh":6,"description":148,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":149,"categories":150,"keywords":151,"publishedAt":31},"01M71TXD9MYXZC39HCPP909HTZ","strategy-advisor","High-level strategic thinking and business decision guidance for planning and direction-setting.\nUse when: making strategic decisions, evaluating business options, setting direction, analyzing\ntrade-offs, or when user mentions strategy, business planning, competitive analysis, or long-term planning.","https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog\u002Fblob\u002Fmain\u002F_Product-Apps\u002Fstrategy-advisor\u002FSKILL.md",[],[152,153,154,155,156,157,158,159,160,116,161,162,163,19,164,165,122,166,124,167],"strategy advisor","strategy","advisor","competitive","setting","thinking","planning","direction","trade-offs","long","decision","strategic","business","apps","decisions","trade",{"skillNo":169,"name":170,"nameZh":6,"description":171,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":172,"sourceHtmlUrl":173,"categories":174,"keywords":181,"publishedAt":31},"01M71TWHBT2R1P1FNWTW67ZREP","app-paywall-pilot","Design, audit, debug, and implement App Store-compliant mobile paywalls, subscription flows, pricing screens, trials, offers, feature gates, and subscription lifecycle UX. Use when the user asks to audit my paywall, fix App Store 3.1.2 rejection, improve trial-to-paid, choose plans\u002Fprices\u002Ftrials, review RevenueCat\u002FAdapty\u002FApphud\u002FSuperwall setup, calculate LTV\u002FROAS, or build paywall implementation.","https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog\u002Fblob\u002Fmain\u002F_Product-Apps\u002Ffrom-dosesync\u002Fapp-paywall-pilot\u002FLICENSE","https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog\u002Fblob\u002Fmain\u002F_Product-Apps\u002Ffrom-dosesync\u002Fapp-paywall-pilot\u002FSKILL.md",[175,178],{"categoryNo":176,"categoryName":177,"taxonomyType":69,"taxonomyTypeDesc":70},"01JBSEEDCAT000000000000015","视觉设计",{"categoryNo":179,"categoryName":180,"taxonomyType":80,"taxonomyTypeDesc":81},"01JBSEEDCAT000000000000032","设计师",[182,183,184,185,186,187,188,189,190,191,192,193,122,194,195,196,197,198,199,200],"app","paywall","app paywall pilot","paid","paywalls","prices","choose","flows","fix","improve","design","app store","review","audit","ux","subscription","mobile","my","calculate",{"skillNo":202,"name":203,"nameZh":6,"description":204,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":205,"licenseFileUrl":206,"sourceHtmlUrl":207,"categories":208,"keywords":211,"publishedAt":31},"01M71TWET8GFKEB7ZHJPMQX29V","figma","Use the Figma MCP server to fetch design context, screenshots, variables, and assets from Figma, and to translate Figma nodes into production code. Trigger when a task involves Figma URLs, node IDs, design-to-code implementation, or Figma MCP setup and troubleshooting.","Apache-2.0","https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog\u002Fblob\u002Fmain\u002F_Product-Apps\u002Ffigma\u002FLICENSE.txt","https:\u002F\u002Fgithub.com\u002Fvitalikpestov\u002FSkills-Catalog\u002Fblob\u002Fmain\u002F_Product-Apps\u002Ffigma\u002FSKILL.md",[209,210],{"categoryNo":75,"categoryName":76,"taxonomyType":69,"taxonomyTypeDesc":70},{"categoryNo":179,"categoryName":180,"taxonomyType":80,"taxonomyTypeDesc":81},[203,212,213,214,215,119,192,91,19,122,216,217,25,218,95,219,220,221,222,223],"fetch","ids","mcp setup","translate","mcp server","Variables","task","Nodes","figma mcp","code implementation","node","assets"]