Skip to content

Instantly share code, notes, and snippets.

@slinkardbrandon
Created February 18, 2021 02:38
Show Gist options
  • Save slinkardbrandon/3f2e41cf2ac957e706bc2f518f166f22 to your computer and use it in GitHub Desktop.
Save slinkardbrandon/3f2e41cf2ac957e706bc2f518f166f22 to your computer and use it in GitHub Desktop.
TypeScript padding & margin types
type Without<T, U> = { [P in Exclude<keyof T, keyof U>]?: never };
export type XOR<T, U> = T | U extends object
? (Without<T, U> & U) | (Without<U, T> & T)
: T | U;
export type PaddingValue =
| number
| `${number}px`
| `${number}em`
| `${number}rem`;
export type PaddingX = XOR<
{ x: PaddingValue },
{ left?: PaddingValue; right?: PaddingValue }
>;
export type PaddingY = XOR<
{ y: PaddingValue },
{ top?: PaddingValue; bottom?: PaddingValue }
>;
export type Padding = PaddingX | PaddingY;
export type MarginValue = PaddingValue | "auto";
export type MarginX = XOR<
{ x: PaddingValue },
{ left?: PaddingValue; right?: PaddingValue }
>;
export type MarginY = XOR<
{ y: PaddingValue },
{ top?: PaddingValue; bottom?: PaddingValue }
>;
export type Margin = MarginX | MarginY;
import { Padding } from './types.ts';
const a: Padding = { x: 1, y: 1 } // no error
const b: Padding = { left: 1, right: 1, y: 1 } // no error
const c: Padding = { left: 5, right: 5, bottom: 5, top: 5 }; // no error
const d: Padding = { left: 5, x: 5 } // error
const e: Padding = { top: 5, x: 5 } // no error
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment