Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

allow string literals for enums! #2484

Merged
merged 14 commits into from
May 21, 2018
11 changes: 6 additions & 5 deletions packages/core/src/common/alignment.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,9 @@
*/

/** Alignment along the horizontal axis. */
export enum Alignment {
CENTER = "center",
LEFT = "left",
RIGHT = "right",
}
export const Alignment = {
CENTER: "center" as "center",
LEFT: "left" as "left",
RIGHT: "right" as "right",
};
export type Alignment = typeof Alignment[keyof typeof Alignment];
13 changes: 13 additions & 0 deletions packages/core/src/common/boundary.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
/*
* Copyright 2018 Palantir Technologies, Inc. All rights reserved.
*
* Licensed under the terms of the LICENSE file distributed with this project.
*/

/** Boundary of a one-dimensional interval. */
export const Boundary = {
START: "start" as "start",
// tslint:disable-next-line:object-literal-sort-keys
END: "end" as "end",
};
export type Boundary = typeof Boundary[keyof typeof Boundary];
4 changes: 2 additions & 2 deletions packages/core/src/common/classes.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,8 @@
* Licensed under the terms of the LICENSE file distributed with this project.
*/

import { Elevation } from "../components/card/card";
import { Alignment } from "./alignment";
import { Elevation } from "./elevation";
import { Intent } from "./intent";

const NS = process.env.BLUEPRINT_NAMESPACE || "bp3";
Expand Down Expand Up @@ -271,7 +271,7 @@ export function iconClass(iconName?: string) {
}

/** Return CSS class for intent. */
export function intentClass(intent = Intent.NONE) {
export function intentClass(intent?: Intent) {
if (intent == null || intent === Intent.NONE) {
return undefined;
}
Expand Down
15 changes: 15 additions & 0 deletions packages/core/src/common/elevation.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
/*
* Copyright 2018 Palantir Technologies, Inc. All rights reserved.
*
* Licensed under the terms of the LICENSE file distributed with this project.
*/

// tslint:disable:object-literal-sort-keys
export const Elevation = {
ZERO: 0 as 0,
ONE: 1 as 1,
TWO: 2 as 2,
THREE: 3 as 3,
FOUR: 4 as 4,
};
export type Elevation = typeof Elevation[keyof typeof Elevation];
2 changes: 2 additions & 0 deletions packages/core/src/common/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,10 @@
export * from "./abstractComponent";
export * from "./abstractPureComponent";
export * from "./alignment";
export * from "./boundary";
export * from "./colors";
export * from "./constructor";
export * from "./elevation";
export * from "./intent";
export * from "./position";
export * from "./props";
Expand Down
17 changes: 10 additions & 7 deletions packages/core/src/common/intent.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,16 @@
* Licensed under the terms of the LICENSE file distributed with this project.
*/

// tslint:disable:object-literal-sort-keys

/**
* The four basic intents.
*/
export enum Intent {
NONE = "none",
PRIMARY = "primary",
SUCCESS = "success",
WARNING = "warning",
DANGER = "danger",
}
export const Intent = {
NONE: "none" as "none",
PRIMARY: "primary" as "primary",
SUCCESS: "success" as "success",
WARNING: "warning" as "warning",
DANGER: "danger" as "danger",
};
export type Intent = typeof Intent[keyof typeof Intent];
29 changes: 15 additions & 14 deletions packages/core/src/common/position.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,20 +4,21 @@
* Licensed under the terms of the LICENSE file distributed with this project.
*/

export enum Position {
TOP_LEFT = "top-left",
TOP = "top",
TOP_RIGHT = "top-right",
RIGHT_TOP = "right-top",
RIGHT = "right",
RIGHT_BOTTOM = "right-bottom",
BOTTOM_RIGHT = "bottom-right",
BOTTOM = "bottom",
BOTTOM_LEFT = "bottom-left",
LEFT_BOTTOM = "left-bottom",
LEFT = "left",
LEFT_TOP = "left-top",
}
export const Position = {
BOTTOM: "bottom" as "bottom",
BOTTOM_LEFT: "bottom-left" as "bottom-left",
BOTTOM_RIGHT: "bottom-right" as "bottom-right",
LEFT: "left" as "left",
LEFT_BOTTOM: "left-bottom" as "left-bottom",
LEFT_TOP: "left-top" as "left-top",
RIGHT: "right" as "right",
RIGHT_BOTTOM: "right-bottom" as "right-bottom",
RIGHT_TOP: "right-top" as "right-top",
TOP: "top" as "top",
TOP_LEFT: "top-left" as "top-left",
TOP_RIGHT: "top-right" as "top-right",
};
export type Position = typeof Position[keyof typeof Position];

export function isPositionHorizontal(position: Position) {
/* istanbul ignore next */
Expand Down
9 changes: 1 addition & 8 deletions packages/core/src/components/card/card.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
import classNames from "classnames";
import * as React from "react";
import * as Classes from "../../common/classes";
import { Elevation } from "../../common/elevation";
import { HTMLDivProps, IProps } from "../../common/props";

export interface ICardProps extends IProps, HTMLDivProps {
Expand Down Expand Up @@ -37,14 +38,6 @@ export interface ICardProps extends IProps, HTMLDivProps {
onClick?: (e: React.MouseEvent<HTMLDivElement>) => void;
}

export enum Elevation {
ZERO = 0,
ONE = 1,
TWO = 2,
THREE = 3,
FOUR = 4,
}

export class Card extends React.PureComponent<ICardProps, {}> {
public static displayName = "Blueprint2.Card";
public static defaultProps: ICardProps = {
Expand Down
14 changes: 7 additions & 7 deletions packages/core/src/components/collapse/collapse.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -42,18 +42,18 @@ export interface ICollapseProps extends IProps {

export interface ICollapseState {
/** The height that should be used for the content animations. This is a CSS value, not just a number. */
height?: string;
height: string;

/** The state the element is currently in. */
animationState?: AnimationStates;
animationState: AnimationStates;
}

export enum AnimationStates {
CLOSED = "closed",
OPENING = "opening",
OPEN = "open",
CLOSING_START = "closing-start",
CLOSING_END = "closing-end",
CLOSED,
OPENING,
OPEN,
CLOSING_START,
CLOSING_END,
}

/*
Expand Down
24 changes: 10 additions & 14 deletions packages/core/src/components/collapsible-list/collapsibleList.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
import classNames from "classnames";
import * as React from "react";

import { Boundary } from "../../common/boundary";
import * as Classes from "../../common/classes";
import * as Errors from "../../common/errors";
import { Position } from "../../common/position";
Expand All @@ -18,11 +19,6 @@ import { IPopoverProps, Popover } from "../popover/popover";

type CollapsibleItem = React.ReactElement<IMenuItemProps>;

export enum CollapseFrom {
START = "start",
END = "end",
}

export interface ICollapsibleListProps extends IProps {
/**
* Element to render as dropdown target with `CLICK` interaction to show collapsed menu.
Expand All @@ -42,9 +38,9 @@ export interface ICollapsibleListProps extends IProps {

/**
* Which direction the items should collapse from: start or end of the children.
* @default CollapseFrom.START
* @default Boundary.START
*/
collapseFrom?: CollapseFrom;
collapseFrom?: Boundary;

/**
* CSS class names to add to `<li>` tags containing each visible item and the dropdown.
Expand All @@ -62,7 +58,7 @@ export class CollapsibleList extends React.Component<ICollapsibleListProps, {}>
public static displayName = "Blueprint2.CollapsibleList";

public static defaultProps: ICollapsibleListProps = {
collapseFrom: CollapseFrom.START,
collapseFrom: Boundary.START,
dropdownTarget: null,
visibleItemCount: 3,
visibleItemRenderer: null,
Expand All @@ -74,22 +70,22 @@ export class CollapsibleList extends React.Component<ICollapsibleListProps, {}>
const [visibleChildren, collapsedChildren] = this.partitionChildren();

const visibleItems = visibleChildren.map((child: CollapsibleItem, index: number) => {
const absoluteIndex = collapseFrom === CollapseFrom.START ? childrenLength - 1 - index : index;
const absoluteIndex = collapseFrom === Boundary.START ? childrenLength - 1 - index : index;
return (
<li className={this.props.visibleItemClassName} key={absoluteIndex}>
{this.props.visibleItemRenderer(child.props, absoluteIndex)}
</li>
);
});
if (collapseFrom === CollapseFrom.START) {
if (collapseFrom === Boundary.START) {
// reverse START list so separators appear before items
visibleItems.reverse();
}

// construct dropdown menu for collapsed items
let collapsedPopover: JSX.Element;
if (collapsedChildren.length > 0) {
const position = collapseFrom === CollapseFrom.END ? Position.BOTTOM_RIGHT : Position.BOTTOM_LEFT;
const position = collapseFrom === Boundary.END ? Position.BOTTOM_RIGHT : Position.BOTTOM_LEFT;
collapsedPopover = (
<li className={this.props.visibleItemClassName}>
<Popover
Expand All @@ -105,9 +101,9 @@ export class CollapsibleList extends React.Component<ICollapsibleListProps, {}>

return (
<ul className={classNames(Classes.COLLAPSIBLE_LIST, this.props.className)}>
{collapseFrom === CollapseFrom.START ? collapsedPopover : null}
{collapseFrom === Boundary.START ? collapsedPopover : null}
{visibleItems}
{collapseFrom === CollapseFrom.END ? collapsedPopover : null}
{collapseFrom === Boundary.END ? collapsedPopover : null}
</ul>
);
}
Expand All @@ -123,7 +119,7 @@ export class CollapsibleList extends React.Component<ICollapsibleListProps, {}>
}
return React.cloneElement(child as JSX.Element, { key: `visible-${index}` });
});
if (this.props.collapseFrom === CollapseFrom.START) {
if (this.props.collapseFrom === Boundary.START) {
// reverse START list so we can always slice visible items from the front of the list
childrenArray.reverse();
}
Expand Down
2 changes: 1 addition & 1 deletion packages/core/src/components/forms/numericInput.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ export interface INumericInputProps extends IIntentProps, IProps {
* The position of the buttons with respect to the input field.
* @default Position.RIGHT
*/
buttonPosition?: Position.LEFT | Position.RIGHT | "none";
buttonPosition?: typeof Position.LEFT | typeof Position.RIGHT | "none";

/**
* Whether the value should be clamped to `[min, max]` on blur.
Expand Down
13 changes: 7 additions & 6 deletions packages/core/src/components/popover/popover.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,12 +24,13 @@ import { arrowOffsetModifier, getTransformOrigin } from "./popperUtils";
// re-export this symbol for library consumers
export { PopperModifiers };

export enum PopoverInteractionKind {
CLICK = "click",
CLICK_TARGET_ONLY = "click-target",
HOVER = "hover",
HOVER_TARGET_ONLY = "hover-target",
}
export const PopoverInteractionKind = {
CLICK: "click" as "click",
CLICK_TARGET_ONLY: "click-target" as "click-target",
HOVER: "hover" as "hover",
HOVER_TARGET_ONLY: "hover-target" as "hover-target",
};
export type PopoverInteractionKind = typeof PopoverInteractionKind[keyof typeof PopoverInteractionKind];

export interface IPopoverProps extends IOverlayableProps, IProps {
/** HTML props for the backdrop element. Can be combined with `backdropClassName`. */
Expand Down
12 changes: 6 additions & 6 deletions packages/core/src/components/toast/toaster.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,12 +20,12 @@ import { IToastProps, Toast } from "./toast";

export type IToastOptions = IToastProps & { key?: string };
export type ToasterPosition =
| Position.TOP
| Position.TOP_LEFT
| Position.TOP_RIGHT
| Position.BOTTOM
| Position.BOTTOM_LEFT
| Position.BOTTOM_RIGHT;
| typeof Position.TOP
| typeof Position.TOP_LEFT
| typeof Position.TOP_RIGHT
| typeof Position.BOTTOM
| typeof Position.BOTTOM_LEFT
| typeof Position.BOTTOM_RIGHT;

/** Instance methods available on a `<Toaster>` component instance. */
export interface IToaster {
Expand Down
18 changes: 9 additions & 9 deletions packages/core/test/collapsible-list/collapsibleListTests.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ import * as React from "react";
import { spy } from "sinon";

import {
CollapseFrom,
Boundary,
CollapsibleList,
ICollapsibleListProps,
IMenuItemProps,
Expand Down Expand Up @@ -41,8 +41,8 @@ describe("<CollapsibleList>", () => {
assert.strictEqual(popover.prop("position"), Position.TOP_LEFT);
});

it("CollapseFrom.START renders popover target first", () => {
const list = renderCollapsibleList(5, { collapseFrom: CollapseFrom.START });
it("Boundary.START renders popover target first", () => {
const list = renderCollapsibleList(5, { collapseFrom: Boundary.START });
assert.strictEqual(
list
.find("ul")
Expand All @@ -53,8 +53,8 @@ describe("<CollapsibleList>", () => {
);
});

it("CollapseFrom.END renders popover target last", () => {
const list = renderCollapsibleList(5, { collapseFrom: CollapseFrom.END });
it("Boundary.END renders popover target last", () => {
const list = renderCollapsibleList(5, { collapseFrom: Boundary.END });
assert.strictEqual(
list
.find("ul")
Expand Down Expand Up @@ -92,15 +92,15 @@ describe("<CollapsibleList>", () => {
it("is called with props of each child", () => {
const visibleItemRenderer = spy();
// using END so it won't reverse the list
renderCollapsibleList(5, { collapseFrom: CollapseFrom.END, visibleItemRenderer, visibleItemCount: 3 });
renderCollapsibleList(5, { collapseFrom: Boundary.END, visibleItemRenderer, visibleItemCount: 3 });
assert.equal(visibleItemRenderer.callCount, 3);
visibleItemRenderer.args.map((arg, index) => {
const props: IMenuItemProps = arg[0];
assert.deepEqual(props.text, `Item ${index}`);
});
});

it("is called with absolute index of item in props array when CollapseFrom.START", () => {
it("is called with absolute index of item in props array when Boundary.START", () => {
const visibleItemRenderer = spy();
renderCollapsibleList(7, { visibleItemRenderer, visibleItemCount: 3 });
visibleItemRenderer.args.map(arg => {
Expand All @@ -110,9 +110,9 @@ describe("<CollapsibleList>", () => {
});
});

it("is called with absolute index of item in props array when CollapseFrom.END", () => {
it("is called with absolute index of item in props array when Boundary.END", () => {
const visibleItemRenderer = spy();
renderCollapsibleList(6, { collapseFrom: CollapseFrom.END, visibleItemRenderer, visibleItemCount: 3 });
renderCollapsibleList(6, { collapseFrom: Boundary.END, visibleItemRenderer, visibleItemCount: 3 });
visibleItemRenderer.args.map(arg => {
const props: IMenuItemProps = arg[0];
const absoluteIndex = +props.text.toString().slice(5); // "Item #"
Expand Down
5 changes: 0 additions & 5 deletions packages/datetime/src/common/dateUtils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,6 @@ import { Months } from "./months";

export type DateRange = [Date | undefined, Date | undefined];

export enum DateRangeBoundary {
START = "start",
END = "end",
}

export function isDateValid(date: Date | false | null): date is Date {
return date instanceof Date && !isNaN(date.valueOf());
}
Expand Down
Loading