Responsive and Theme-Variable UI: Where Decisions Run

Material UI can adapt an interface in two different senses. A component can keep the same structure while its CSS changes with the viewport, or the application can choose a different color scheme while the browser keeps the component logic stable. This chapter follows where those decisions run: how sx turns theme-aware responsive intent into CSS, and how CSS variables move color-scheme work from JavaScript into generated styles. The goal is to choose between CSS and JavaScript for a reason, then weigh the SSR and performance consequences of that choice.

Responsive Values: CSS Until the Rendering Tree Must Change

Responsive design begins with a shared question: at which widths should a layout change? Material UI treats breakpoints as theme values rather than as isolated numbers hidden inside each component. The documentation describes the library as mobile-first and uses the same breakpoint helpers both inside components and in application layout. This lets a product define a vocabulary such as small, medium, or large once, then use that vocabulary in multiple places.

The sx system is the translation layer. Its input can look like ordinary CSS, but it also accepts a function of the theme, an array of responsive values, or an object whose keys are breakpoints. The system resolves a function against the current theme, maps configured properties through theme values and transforms, creates breakpoint branches, expands responsive values into media queries, and recursively processes nested styles. The result is CSS that the browser can apply without requiring each component to implement its own breakpoint parser.

That sequence explains why a short responsive rule can still be part of a design system. A spacing value can be interpreted through the theme’s spacing function rather than copied as a final pixel length. A breakpoint-keyed value can be assigned at named breakpoints rather than at arbitrary widths. A responsive array can express a mobile-first progression while an object can make the breakpoint conditions explicit. The syntax stays close to CSS, but the meaning comes from the same theme that other components use.

Imagine a Box that should have compact padding on a small screen and wider padding at a larger breakpoint. The application supplies a responsive value; the system finds the theme’s spacing and breakpoint definitions, creates the base rule, adds the media-query branch, and removes any unused breakpoint branches. The component does not need to know whether the product’s medium screen begins at the library default or at a custom value. That decision belongs to the theme. The resulting CSS is still ordinary browser CSS, so the browser can respond without a React state update.

The mechanism also has a clear stopping point. CSS is enough when the component tree remains conceptually the same and only presentation changes. A card can change from a row to a column, a grid can change its columns, or a control can change its spacing without JavaScript deciding which elements exist. In these cases, keeping the decision in CSS avoids adding a second runtime state and allows the browser to respond directly to its viewport.

JavaScript becomes relevant when the rendering tree itself must change. Material UI documents useMediaQuery for cases where CSS alone is not enough and the application needs the breakpoint value in JavaScript. That might mean rendering a different branch, choosing a different data strategy, or coordinating behavior that cannot be expressed as a style. The distinction is not that one method is modern and the other is old.