Mastering React Advanced Hooks with TypeScript: Simulating a Dynamic Equation System
In today’s React applications, advanced hooks like useContext, useReducer, and useLayoutEffect provide powerful tools to manage state, coordinate rendering, and share data efficiently—without introducing excessive boilerplate.
In this article, we’ll implement these hooks in a real-world mathematical scenario: simulating a system of equations with shared coefficients and synchronized updates using React + TypeScript.
Objective: Simulate and Manage Dynamic Equations
We’ll create a dynamic environment with:
- Global equation context using
useContext - State transitions and actions using
useReducer - Layout synchronization using
useLayoutEffectto ensure DOM alignment before render
Hook Overview in this Context
| Hook | Purpose |
|---|---|
useContext |
Share coefficients across components |
useReducer |
Manage complex state transitions like equation switching |
useLayoutEffect |
Ensure the canvas and equation list align correctly before paint |
Step 1: Define Global Math Context
// MathContext.tsx
import React, { createContext, useReducer, useContext } from "react";
type Equation = {
id: string;
formula: string;
coefficients: number[];
};
type State = {
activeEquation: Equation;
};
type Action =
| { type: "SET_EQUATION"; payload: Equation };
const initialState: State = {
activeEquation: {
id: "eq1",
formula: "y = ax² + bx + c",
coefficients: [1, 2, 1]
}
};
const MathContext = createContext<{ state: State; dispatch: React.Dispatch<Action> } | undefined>(undefined);
function mathReducer(state: State, action: Action): State {
switch (action.type) {
case "SET_EQUATION":
return { ...state, activeEquation: action.payload };
default:
return state;
}
}
export const MathProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {
const [state, dispatch] = useReducer(mathReducer, initialState);
return (
<MathContext.Provider value={{ state, dispatch }}>
{children}
</MathContext.Provider>
);
};
export const useMath = () => {
const context = useContext(MathContext);
if (!context) throw new Error("useMath must be used within MathProvider");
return context;
};
Step 2: Visualizing the Equation
import { useLayoutEffect, useRef } from "react";
import { useMath } from "./MathContext";
export const EquationVisualizer = () => {
const canvasRef = useRef<HTMLCanvasElement | null>(null);
const { state } = useMath();
const [a, b, c] = state.activeEquation.coefficients;
useLayoutEffect(() => {
const canvas = canvasRef.current;
const ctx = canvas?.getContext("2d");
if (!canvas || !ctx) return;
ctx.clearRect(0, 0, canvas.width, canvas.height);
ctx.beginPath();
for (let x = -100; x <= 100; x++) {
const px = canvas.width / 2 + x;
const y = a * x * x + b * x + c;
const py = canvas.height / 2 - y;
x === -100 ? ctx.moveTo(px, py) : ctx.lineTo(px, py);
}
ctx.strokeStyle = "teal";
ctx.lineWidth = 2;
ctx.stroke();
}, [a, b, c]);
return <canvas ref={canvasRef} width={400} height={400} style={{ border: "1px solid gray" }} />;
};
Step 3: Dynamic Equation Switching
const EquationSelector = () => {
const { dispatch } = useMath();
const handleChange = () => {
dispatch({
type: "SET_EQUATION",
payload: {
id: "eq2",
formula: "y = 2x² - 3x + 5",
coefficients: [2, -3, 5]
}
});
};
return <button onClick={handleChange}>Switch Equation</button>;
};
App Component
import { MathProvider } from "./MathContext";
import { EquationVisualizer } from "./EquationVisualizer";
import { EquationSelector } from "./EquationSelector";
export const App = () => (
<MathProvider>
<h1>🧠 Equation Simulation</h1>
<EquationSelector />
<EquationVisualizer />
</MathProvider>
);
Key Concepts Illustrated
| Hook | Role in Simulation |
|---|---|
useReducer |
Equation state machine |
useContext |
Shared equation access across components |
useLayoutEffect |
Canvas DOM render before paint |
canvas + TS |
Visualize mathematical curves |
TypeScript |
Precise modeling of equations |
Conclusion
React’s advanced hooks offer the flexibility and structure needed to simulate real-world systems, including mathematical and scientific processes.
By combining useContext, useReducer, and useLayoutEffect, we:
- Centralized state using reducers
- Propagated updates globally with context
- Ensured DOM synchronization before drawing equations
React isn’t just for UIs—it’s a powerful platform for modeling logic-heavy systems.
Next: Learn how to build a matrix visualizer using useMemo + useCallback + SVG.
Tags: react typescript useReducer useContext useLayoutEffect math canvas simulation frontend

Top comments (0)