Author Components in .css.ts Files Co-Located With React Source — Typed Props and Variants Included
Using Salty CSS in React Components
Create components
Salty CSS only picks up files whose names end with one of these suffixes:
| Suffix | When to use it |
|---|---|
.css.ts | Default for any style or component file. Works everywhere. |
.css.tsx | Same as .css.ts, but JSX is allowed in the file. |
.salty.ts | Alias of .css.ts — pick whichever reads better in your project. |
.styled.ts | Alias of .css.ts, conventionally used for styled factories. |
.styles.ts | Alias of .css.ts, conventionally used for defineTemplates etc. |
A .ts file with the same content but missing the right suffix will type-check fine but produce no CSS at build time — this is the single most common "my styles aren't appearing" cause. See Troubleshooting if you hit it.
Component structure
// /components/my-component.css.ts import { styled } from "@salty-css/react/styled"; export const Component = styled("div", { className: "wrapper", // Optional custom class name element: "section", // Optional override for the rendered HTML element base: { // Base styles that are always applied display: "flex", padding: "1rem", backgroundColor: "#f5f5f5", }, variants: { // Conditional styles based on props size: { small: { padding: "0.5rem" }, large: { padding: "2rem" }, }, color: { primary: { backgroundColor: "blue", color: "white" }, secondary: { backgroundColor: "gray", color: "black" }, }, }, compoundVariants: [ // Styles applied when multiple variant conditions are met { size: "small", color: "primary", css: { borderRadius: "4px" }, }, ], });
Using components
import { Component } from "./my-component.css"; const MyPage = () => { return ( <Component size="small" color="primary"> This is a Salty CSS component </Component> ); }; export default MyPage;
Naming components in DevTools
In development builds, every styled component renders with a data-component-name attribute matching its export name. Search for [data-component-name="Button"] in the elements panel to jump straight to it. You can override the label with the displayName option on the styled definition:
export const PrimaryButton = styled("button", { displayName: "PrimaryButton", base: { /* … */ }, });
In production builds the attribute is stripped, so it's a debugging aid only.
Where to go next
- Add prop-driven styles → Variants (and
anyOfVariantsfor OR-logic). - Share style bundles across components → Templates.
- Add design tokens → Variables.
- Add dark mode → Theming.
- Extend a third-party component → Overrides.
- API reference →
styled·className·defineConfig.
Demo Projects
- Next.js Demo Project: View on GitHub
- React + Vite Demo: View on GitHub
- CodeSandbox Demo: