I'm trying to extend Theme with Material UI, but it's throwing an error, saying that I'm not extending it correctly, saying,
Property 'layout' is missing in type 'Palette' but required in type 'IPaletteOptions'.
Here is what I have:
// src/theme/theme.d.ts
import { Theme } from "@material-ui/core/styles";
import {
IPaletteOptions,
PaletteOptions
} from "@material-ui/core/styles/createPalette";
type TLayout = {
primary: string;
secondary: string;
};
declare module "@material-ui/core/styles/createPalette" {
export interface IPaletteOptions extends PaletteOptions {
layout: TLayout;
}
}
declare module "@material-ui/core/styles" {
export interface ITheme extends Theme {
palette: IPaletteOptions;
}
}
// src/theme/index.ts
import { createMuiTheme, ITheme } from "@material-ui/core/styles";
import { IPaletteOptions } from "@material-ui/core/styles/createPalette";
export const palette = {
layout: {
primary: "#ffffff",
secondary: "#e4e4e4"
}
} as IPaletteOptions;
export default createMuiTheme({ palette }) as ITheme;
// src/App.tsx
import React from "react";
import { ThemeProvider, ITheme } from "@material-ui/core";
import theme from "./theme";
import Component from "./Component";
export default function App() {
return (
<ThemeProvider<ITheme> theme={theme}>
<Component />
</ThemeProvider>
);
}
import { useTheme } from "@material-ui/core";
import React from "react";
export default React.memo(() => {
const theme = useTheme(); // <-- this should be of type `ITheme` automatically
// If I do useTheme<ITheme>(), it shows property 'layout', but
// I shouldn't have to do that, because of the type casting that
// I do in App.tsx, where I import and use 'theme' from src/theme/index.ts
return <div>the layout primary color is {theme.palette.layout.primary}</div>;
});
What am I doing wrong here? I would like to use ITheme throughout my app, which would extend the basic Theme in addition to what I add.