我有一个相当复杂的 React 应用程序 (v18),使用 FluentUI (v8) 并使用 Vite (v5) 构建。 有一组受主题影响的 CSS 变量,但对于我的应用程序来说,它们似乎很大程度上未定义。 我确实定义了
ThemeProvider
。 我会尝试包含相关代码。
const App = () => {
...
const theme = createTheme({
palette: {
themePrimary: '#ff462d',
themeLighterAlt: '#fff8f7',
themeLighter: '#ffe1de',
themeLight: '#ffc8c0',
themeTertiary: '#ff9082',
themeSecondary: '#ff5c47',
themeDarkAlt: '#e63f29',
themeDark: '#c23523',
themeDarker: '#8f271a',
neutralLighterAlt: '#faf9f8',
neutralLighter: '#f3f2f1',
neutralLight: '#edebe9',
neutralQuaternaryAlt: '#e1dfdd',
neutralQuaternary: '#d0d0d0',
neutralTertiaryAlt: '#c8c6c4',
neutralTertiary: '#a19f9d',
neutralSecondary: '#605e5c',
neutralPrimaryAlt: '#3b3a39',
neutralPrimary: '#323130',
neutralDark: '#201f1e',
black: '#000000',
white: '#ffffff',
},
components: {
IconButton: {
styles: {
rootDisabled: {
opacity: 0.5
},
root: {
opacity: 1,
backgroundColor: '#fff'
}
}
}
}
});
...
return (
<FluentProvider theme={webLightTheme}>
<ThemeProvider theme={theme}>
<RouterProvider router={router} />
</ThemeProvider>
</FluentProvider>
);
};
然后我有一个
Callout
,里面有一些 Checkbox
组件:
const filterDialog = (
<Callout
className={styles.filterDialog}
role="dialog"
target={`#${filterButtonId}`}
onDismiss={hideFilters}
>
<Text as="h1" block variant="large">Filters</Text>
<Stack horizontal horizontalAlign="space-between" tokens={{ childrenGap: '5px' }}>
<Checkbox size="large" label={ filterCheckboxLabel("Feedback") } />
<Checkbox disabled={!filterByFeedback} label={ filterCheckboxLabel("Liked?") } />
<Checkbox disabled={!filterByFeedback} label={ filterCheckboxLabel("Disiked?") } />
</Stack>
</Callout>
);
return (
<Stack className={styles.top}>
...
<IconButton id={filterButtonId} disabled={false} onClick={toggleFilters} iconProps={{ iconName: "filter" }} />
{showFilterDialog ? filterDialog : null}
<IconButton disabled={true} iconProps={{ iconName: "trash" }} />
</StackItem>
</Stack>
</StackItem>
...
复选框未正确渲染(间距关闭且复选框边框太粗,所以我查看了开发控制台并看到了这一点:
对于如何诊断问题可能是什么,我有点不知所措......我不是 FluentUI 内部工作原理的专家,希望这里有人是!
更新:我可以看到
FluentProvider
正在设置这些变量...但由于某种原因,复选框样式无法访问它们?
更新:我在这里取得了一些进展...看起来诸如
Callout
之类的表面是在与 FluentProvider
所包装的称为“默认层主机”上下文的单独层次结构中渲染的。 所以问题变成了“如何用 FluentProvider
包装默认层主机上下文?”
该问题是由于
Callout
在单独的层次结构中呈现而引起的。 通过创建自定义 LayerHost
组件并使用 layerProps.hostId
属性将标注指向该组件,我能够在 ThemeProvider
下渲染它:
...
return (
<FluentProvider theme={teamsLightTheme}>
<ThemeProvider theme={theme}>
<RouterProvider router={router} />
<LayerHost id="custom-layer-host" style={{ position: 'fixed', top: 0, left: 0, width: '100%' }} />
</ThemeProvider>
</FluentProvider>
);
...
起初标注是水平展平的,但添加这些样式似乎解决了问题。
这是
Callout
现在的样子:
...
const filterDialog = (
<Callout
className={styles.filterDialog}
role="dialog"
target={`#${filterButtonId}`}
onDismiss={hideFilters}
layerProps={{ hostId: "custom-layer-host", }}
>
<Text as="h1" block variant="large">Filters</Text>
<Stack horizontal horizontalAlign="space-between" tokens={{ childrenGap: '5px' }}>
<Checkbox checked={filterByFeedback} size="large" label={ filterCheckboxLabel("Feedback") } onChange={(_ev, data) => { data.checked ? setFilterByFeedback() : clearFilterByFeedback() }} />
<Checkbox checked={filterByFeedbackPos} disabled={!filterByFeedback} label={ filterCheckboxLabel("Liked?") } onChange={(_ev, data) => { data.checked ? setFilterByFeedbackPos() : clearFilterByFeedbackPos() }} />
<Checkbox checked={filterByFeedbackNeg} disabled={!filterByFeedback} label={ filterCheckboxLabel("Disliked?") } onChange={(_ev, data) => { data.checked ? setFilterByFeedbackNeg() : clearFilterByFeedbackNeg() }} />
</Stack>
</Callout>
);
...