1
0

Wrap.tsx 1.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344
  1. import { ApplicationRef, createComponent, Type, ComponentRef } from '@angular/core';
  2. import { createApplication } from '@angular/platform-browser';
  3. import { HostedComponentContext } from '@vendure/admin-ui/react';
  4. import React, { useContext, useEffect, useRef, useState, PropsWithChildren } from 'react';
  5. type AnyComponentRef = ComponentRef<unknown>;
  6. export function Wrap<T extends Type<any>>(
  7. props: PropsWithChildren<{ cmp: T; inputs?: { [key: string]: any } }>,
  8. ) {
  9. const context = useContext(HostedComponentContext);
  10. const hostRef = useRef<HTMLDivElement>(null);
  11. const [appRef, setAppRef] = useState<ApplicationRef | null>(null);
  12. const [compRef, setCompRef] = useState<AnyComponentRef | null>(null);
  13. useEffect(() => {
  14. void createApplication().then(setAppRef);
  15. return () => appRef?.destroy();
  16. }, []);
  17. useEffect(() => {
  18. if (appRef && hostRef.current) {
  19. setCompRef(
  20. createComponent(props.cmp, {
  21. environmentInjector: appRef!.injector as any,
  22. hostElement: hostRef!.current!,
  23. projectableNodes: [props.children as any],
  24. }),
  25. );
  26. }
  27. return () => compRef?.destroy();
  28. }, [appRef, hostRef, props.cmp]);
  29. useEffect(() => {
  30. if (compRef) {
  31. for (const [key, value] of Object.entries(props.inputs || {})) {
  32. compRef.setInput(key, value);
  33. }
  34. compRef.changeDetectorRef.detectChanges();
  35. }
  36. }, [compRef, props.inputs]);
  37. return <div ref={hostRef} />;
  38. }