diff --git a/libs/components/src/button/button.component.css b/libs/components/src/button/button.component.css new file mode 100644 index 00000000000..caafb60fe4f --- /dev/null +++ b/libs/components/src/button/button.component.css @@ -0,0 +1,106 @@ +.bit-button { + /* Design tokens (default values) scoped to button, referencing tw-theme.css */ + + --bit-color-button-border-width: 2px; + --bit-spacing-button-small-y: 0.25rem; + --bit-spacing-button-small-x: 0.75rem; + --bit-spacing-button-default-y: 0.375rem; + --bit-spacing-button-default-x: 0.75rem; + + --bit-color-button-border-primary: rgb(var(--color-primary-600)); + --bit-color-button-bg-primary: rgb(var(--color-primary-600)); + --bit-color-button-text-primary-contrast: rgb(var(--color-text-contrast)); + --bit-color-button-bg-primary-hover: rgb(var(--color-primary-700)); + --bit-color-button-border-primary-hover: rgb(var(--color-primary-700)); + --bit-color-button-text-primary: rgb(var(--color-primary-600)); + --bit-color-button-bg-hover-default: var(--color-hover-default); + + --bit-color-button-border-danger: rgb(var(--color-danger-600)); + --bit-color-button-text-danger: rgb(var(--color-danger-600)); + --bit-color-button-bg-danger-hover: rgb(var(--color-danger-600)); + --bit-color-button-border-danger-hover: rgb(var(--color-danger-600)); + --bit-color-button-text-danger-contrast: rgb(var(--color-text-contrast)); + + --bit-color-button-primary-600: rgb(var(--color-primary-600)); + --bit-color-button-secondary-300: rgb(var(--color-secondary-300)); + --bit-color-button-text-muted: rgb(var(--color-text-muted)); + + font-weight: 600; + border-radius: 9999px; + transition: all 0.2s; + border-width: var(--bit-btn-border-width); + border-style: solid; + text-align: center; + text-decoration: none; + outline: none; +} + +.bit-button-inline { + display: inline-block; +} + +.bit-button-block { + width: 100%; + display: block; +} + +.bit-button-size-small { + font-size: 0.875rem; + padding-top: var(--bit-spacing-button-small-y); + padding-bottom: var(--bit-spacing-button-small-y); + padding-left: var(--bit-spacing-button-small-x); + padding-right: var(--bit-spacing-button-small-x); +} + +.bit-button-size-default { + padding-top: var(--bit-spacing-button-default-y); + padding-bottom: var(--bit-spacing-button-default-y); + padding-left: var(--bit-spacing-button-default-x); + padding-right: var(--bit-spacing-button-default-x); +} + +.bit-button-primary { + border-color: var(--bit-color-button-border-primary); + background-color: var(--bit-color-button-bg-primary); + color: var(--bit-color-button-text-primary-contrast) !important; +} +.bit-button-primary:hover { + background-color: var(--bit-color-button-bg-primary-hover); + border-color: var(--bit-color-button-border-primary-hover); +} + +.bit-button-secondary { + background-color: transparent; + border-color: var(--bit-color-button-border-primary); + color: var(--bit-color-button-text-primary) !important; +} +.bit-button-secondary:hover { + background-color: var(--bit-color-button-bg-hover-default); +} + +.bit-button-danger { + background-color: transparent; + border-color: var(--bit-color-button-border-danger); + color: var(--bit-color-button-text-danger) !important; +} +.bit-button-danger:hover { + background-color: var(--bit-color-button-bg-danger-hover); + border-color: var(--bit-color-button-border-danger-hover); + color: var(--bit-color-button-text-danger-contrast) !important; +} + +.bit-button-focus-ring:focus-visible { + box-shadow: 0 0 0 2px var(--bit-color-button-primary-600); + z-index: 10; + outline: none; +} + +.bit-button-disabled, +.bit-button-disabled:disabled, +.bit-button-disabled[disabled] { + background-color: var(--bit-color-button-secondary-300) !important; + border-color: var(--bit-color-button-secondary-300) !important; + color: var(--bit-color-button-text-muted) !important; + cursor: not-allowed; + text-decoration: none !important; +} diff --git a/libs/components/src/button/button.component.ts b/libs/components/src/button/button.component.ts index 635c269bd0f..92704fdc68a 100644 --- a/libs/components/src/button/button.component.ts +++ b/libs/components/src/button/button.component.ts @@ -5,43 +5,17 @@ import { debounce, interval } from "rxjs"; import { ButtonLikeAbstraction, ButtonType, ButtonSize } from "../shared/button-like.abstraction"; -const focusRing = [ - "focus-visible:tw-ring-2", - "focus-visible:tw-ring-offset-2", - "focus-visible:tw-ring-primary-600", - "focus-visible:tw-z-10", -]; +const focusRing = ["bit-button-focus-ring"]; const buttonSizeStyles: Record = { - small: ["tw-py-1", "tw-px-3", "tw-text-sm"], - default: ["tw-py-1.5", "tw-px-3"], + small: ["bit-button-size-small"], + default: ["bit-button-size-default"], }; const buttonStyles: Record = { - primary: [ - "tw-border-primary-600", - "tw-bg-primary-600", - "!tw-text-contrast", - "hover:tw-bg-primary-700", - "hover:tw-border-primary-700", - ...focusRing, - ], - secondary: [ - "tw-bg-transparent", - "tw-border-primary-600", - "!tw-text-primary-600", - "hover:tw-bg-hover-default", - ...focusRing, - ], - danger: [ - "tw-bg-transparent", - "tw-border-danger-600", - "!tw-text-danger", - "hover:tw-bg-danger-600", - "hover:tw-border-danger-600", - "hover:!tw-text-contrast", - ...focusRing, - ], + primary: ["bit-button-primary", ...focusRing], + secondary: ["bit-button-secondary", ...focusRing], + danger: ["bit-button-danger", ...focusRing], unstyled: [], }; @@ -56,33 +30,10 @@ const buttonStyles: Record = { }) export class ButtonComponent implements ButtonLikeAbstraction { @HostBinding("class") get classList() { - return [ - "tw-font-semibold", - "tw-rounded-full", - "tw-transition", - "tw-border-2", - "tw-border-solid", - "tw-text-center", - "tw-no-underline", - "hover:tw-no-underline", - "focus:tw-outline-none", - ] - .concat(this.block() ? ["tw-w-full", "tw-block"] : ["tw-inline-block"]) + return ["bit-button"] + .concat(this.block() ? ["bit-button-block"] : ["bit-button-inline"]) .concat(buttonStyles[this.buttonType() ?? "secondary"]) - .concat( - this.showDisabledStyles() || this.disabled() - ? [ - "disabled:tw-bg-secondary-300", - "disabled:hover:tw-bg-secondary-300", - "disabled:tw-border-secondary-300", - "disabled:hover:tw-border-secondary-300", - "disabled:!tw-text-muted", - "disabled:hover:!tw-text-muted", - "disabled:tw-cursor-not-allowed", - "disabled:hover:tw-no-underline", - ] - : [], - ) + .concat(this.showDisabledStyles() || this.disabled() ? ["bit-button-disabled"] : []) .concat(buttonSizeStyles[this.size() || "default"]); } diff --git a/libs/components/src/tw-theme.css b/libs/components/src/tw-theme.css index fc85dcda3bd..8afa86f7cec 100644 --- a/libs/components/src/tw-theme.css +++ b/libs/components/src/tw-theme.css @@ -5,6 +5,7 @@ @import "./toast/toast.tokens.css"; @import "./toast/toastr.css"; @import "./search/search.component.css"; +@import "./button/button.component.css"; :root { --color-transparent-hover: rgb(0 0 0 / 0.02);