I am trying to avoid prop drilling in my Solid application, but contexts all return undefined or my check throws an error.
SettingsContext.tsx
import {
createContext,
useContext,
createSignal,
type JSX,
Accessor,
Setter,
} from "solid-js";
export const SettingsContext = createContext<SettingsContextType>();
export const SettingsContextProvider = ({
children,
}: {
children: JSX.Element | JSX.Element[];
}) => {
const [settings, setSettings] = createSignal<Settings>({
...
});
const [isPlaying, setIsPlaying] = createSignal(false);
const [state, setState] = createSignal("setup");
const [text, setText] = createSignal(
``,
);
return (
<SettingsContext.Provider
value={{
settings,
setSettings,
isPlaying,
setIsPlaying,
state,
setState,
text,
setText,
}}
>
{children}
</SettingsContext.Provider>
);
};
export const useSettings = () => {
const context = useContext(SettingsContext);
if (!context) {
throw new Error("useSettings must be used within a SettingsProvider");
}
return context;
}
I did also try just using `useContent(SettingsContext)˙ directly.
App.tsx
import {
SettingsContextProvider,
} from "./contexts/SettingsContext";
import AppContent from "./components/AppContent";
export default function App() {
return (
<SettingsContextProvider>
<AppContent />
</SettingsContextProvider>
);
}
I seperated the App.tsx
, as I attempt to fix it. I used it in index.tsx
too.
AppContent.tsx
import { useSettings } from "../contexts/SettingsContext";
export default function AppContent() {
const { state, setState } = useSettings();
}
That is because of the prop destructuring which changes the execution order, making the enclosed children run before the parent, not receiving the context value on time.
You can see this answer for a detailed explanation: https://stackoverflow.com/a/76995880/7134134