code.tsx 1.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354
  1. import { type FileContents, File, FileOptions, LineAnnotation } from "@pierre/precision-diffs"
  2. import { ComponentProps, createEffect, splitProps } from "solid-js"
  3. export type CodeProps<T = {}> = FileOptions<T> & {
  4. file: FileContents
  5. annotations?: LineAnnotation<T>[]
  6. class?: string
  7. classList?: ComponentProps<"div">["classList"]
  8. }
  9. export function Code<T>(props: CodeProps<T>) {
  10. let container!: HTMLDivElement
  11. const [local, others] = splitProps(props, ["file", "class", "classList", "annotations"])
  12. createEffect(() => {
  13. const instance = new File<T>({
  14. theme: { dark: "oc-1-dark", light: "oc-1-light" },
  15. // theme: { dark: "pierre-dark", light: "pierre-light" },
  16. overflow: "wrap", // or 'scroll'
  17. themeType: "system", // 'system', 'light', or 'dark'
  18. disableFileHeader: true,
  19. disableLineNumbers: false, // optional
  20. // lang: 'typescript', // optional - auto-detected from filename if not provided
  21. ...others,
  22. })
  23. container.innerHTML = ""
  24. instance.render({
  25. file: local.file,
  26. lineAnnotations: local.annotations,
  27. containerWrapper: container,
  28. })
  29. })
  30. return (
  31. <div
  32. data-component="code"
  33. style={{
  34. "--pjs-font-family": "var(--font-family-mono)",
  35. "--pjs-font-size": "var(--font-size-small)",
  36. "--pjs-line-height": "24px",
  37. "--pjs-tab-size": 2,
  38. "--pjs-font-features": "var(--font-family-mono--font-feature-settings)",
  39. "--pjs-header-font-family": "var(--font-family-sans)",
  40. "--pjs-gap-block": 0,
  41. }}
  42. classList={{
  43. ...(local.classList || {}),
  44. [local.class ?? ""]: !!local.class,
  45. }}
  46. ref={container}
  47. />
  48. )
  49. }