javascript - ¿Por qué getPopupContainer no funciona correctamente en mi aplicación de react?
Estoy recibiendo esta advertencia:
Advertencia: [antd: Modal] La función estática no puede consumir el contexto como un tema dinámico. Por favor, utilice el componente 'App' en su lugar.
Entonces, el Modal.confirm() no se muestra correctamente porque se renderiza fuera del árbol de dependencias y no hereda los estilos.
Estoy usando react 18.2.0 y antd 5.4.6.
Aquí dejo el código
main.tsx
ReactDOM.createRoot(document.getElementById('root') as HTMLElement).render(
<Suspense fallback={<Loader />}>
<ThemeWrapper>
<Outlet />
</ThemeCoWrapper>
</Suspense>
);
const ThemeWrapper: React.FC<ThemeProps> = ({ children }) => {
const [theme, setTheme] = useState<any>(defaultTheme);
const modalContainerRef = useRef<HTMLDivElement>(null);
return (
<ConfigProvider
theme={theme}
getPopupContainer={() => modalContainerRef.current as HTMLElement}
>
<div ref={modalContainerRef}>{children}</div>
</ConfigProvider>
);
};
export default ThemeWrapper;
Ejemplo de función en la que utilizo Modal.confirm() dentro del envoltorio
const onLogout = () => {
Modal.confirm({
title: (
<b>
{intl.formatMessage({
id: 'labelCloseSession',
})}
</b>
),
content: intl.formatMessage({
id: 'labelLogoutConfirm',
}),
centered: true,
onOk: async () => {
try {
await loginService.logout();
removeUserSession();
globalContext.dispatch({
type: GlobalStateActionType.LOGOUT,
});
navigate('/login');
} catch (error) {}
},
});
};
Intenté usar document.getElemetById en lugar de useRef, pero no funcionó.
Respuesta #1
Porque la función estática en el modo concurrente de React 18 no será bien soportada. En la v5, Antd recomienda usar hooks para la sustitución estática (lea aquí). Por lo tanto, necesitará configurar su proyecto como lo indicaron aquí: https://ant.design/components/app#basic-usage
En tu caso, prueba:
- Para el componente
ThemeWrapper import { App } from 'antd';Y luego, envuelve el elemento
<div>en<App></App>así:<ConfigProvider theme={theme} getPopupContainer={() => modalContainerRef.current as HTMLElement} > <App> <div ref={modalContainerRef}>{children}</div> </App> </ConfigProvider>
Aquí, proporciono el ejemplo de codesandbox: https://codesandbox.io/s/text-and-link-component-antd-5-0-2-forked-9svf8v?file=/demo.tsx Recomiendan encapsular App en el nivel superior de la aplicación
Después de eso, necesitarás usar modal.confirm({}) de App.useApp(); en lugar del antiguo Modal.confirm() en tu función onLogout.
