Add color picker component and tidy up style options
This commit is contained in:
parent
dd4c7a186e
commit
4b9a863c68
|
@ -0,0 +1,218 @@
|
||||||
|
<script>
|
||||||
|
import { createEventDispatcher } from "svelte"
|
||||||
|
import "@spectrum-css/popover/dist/index-vars.css"
|
||||||
|
import clickOutside from "../Actions/click_outside"
|
||||||
|
import { fly } from "svelte/transition"
|
||||||
|
import Icon from "../Icon/Icon.svelte"
|
||||||
|
import Input from "../Form/Input.svelte"
|
||||||
|
import { capitalise } from "helpers"
|
||||||
|
|
||||||
|
export let value
|
||||||
|
|
||||||
|
let open = false
|
||||||
|
|
||||||
|
$: color = value || "transparent"
|
||||||
|
$: customValue = getCustomValue(value)
|
||||||
|
$: checkColor = getCheckColor(value)
|
||||||
|
|
||||||
|
const dispatch = createEventDispatcher()
|
||||||
|
const categories = [
|
||||||
|
{
|
||||||
|
label: "Grays",
|
||||||
|
colors: [
|
||||||
|
"white",
|
||||||
|
"gray-50",
|
||||||
|
"gray-75",
|
||||||
|
"gray-100",
|
||||||
|
"gray-200",
|
||||||
|
"gray-300",
|
||||||
|
"gray-400",
|
||||||
|
"gray-500",
|
||||||
|
"gray-600",
|
||||||
|
"gray-700",
|
||||||
|
"gray-800",
|
||||||
|
"gray-900",
|
||||||
|
"black",
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "Colors",
|
||||||
|
colors: [
|
||||||
|
"red-400",
|
||||||
|
"orange-400",
|
||||||
|
"yellow-400",
|
||||||
|
"green-400",
|
||||||
|
"seafoam-400",
|
||||||
|
"blue-400",
|
||||||
|
"indigo-400",
|
||||||
|
"magenta-400",
|
||||||
|
|
||||||
|
"red-500",
|
||||||
|
"orange-500",
|
||||||
|
"yellow-500",
|
||||||
|
"green-500",
|
||||||
|
"seafoam-500",
|
||||||
|
"blue-500",
|
||||||
|
"indigo-500",
|
||||||
|
"magenta-500",
|
||||||
|
|
||||||
|
"red-600",
|
||||||
|
"orange-600",
|
||||||
|
"yellow-600",
|
||||||
|
"green-600",
|
||||||
|
"seafoam-600",
|
||||||
|
"blue-600",
|
||||||
|
"indigo-600",
|
||||||
|
"magenta-600",
|
||||||
|
|
||||||
|
"red-700",
|
||||||
|
"orange-700",
|
||||||
|
"yellow-700",
|
||||||
|
"green-700",
|
||||||
|
"seafoam-700",
|
||||||
|
"blue-700",
|
||||||
|
"indigo-700",
|
||||||
|
"magenta-700",
|
||||||
|
],
|
||||||
|
},
|
||||||
|
]
|
||||||
|
|
||||||
|
const onChange = value => {
|
||||||
|
dispatch("change", value)
|
||||||
|
open = false
|
||||||
|
}
|
||||||
|
|
||||||
|
const getCustomValue = value => {
|
||||||
|
if (!value) {
|
||||||
|
return value
|
||||||
|
}
|
||||||
|
let found = false
|
||||||
|
const comparisonValue = value.substring(35, value.length - 1)
|
||||||
|
for (let category of categories) {
|
||||||
|
found = category.colors.includes(comparisonValue)
|
||||||
|
if (found) {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return found ? null : value
|
||||||
|
}
|
||||||
|
|
||||||
|
const prettyPrint = color => {
|
||||||
|
return capitalise(color.split("-").join(" "))
|
||||||
|
}
|
||||||
|
|
||||||
|
const getCheckColor = value => {
|
||||||
|
return /^.*(white|(gray-(50|75|100|200|300|400|500)))\)$/.test(value)
|
||||||
|
? "black"
|
||||||
|
: "white"
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div
|
||||||
|
class="preview"
|
||||||
|
style="background: {color};"
|
||||||
|
on:click={() => (open = true)}
|
||||||
|
/>
|
||||||
|
{#if open}
|
||||||
|
<div
|
||||||
|
use:clickOutside={() => (open = false)}
|
||||||
|
transition:fly={{ y: -20, duration: 200 }}
|
||||||
|
class="spectrum-Popover spectrum-Popover--bottom spectrum-Picker-popover is-open"
|
||||||
|
>
|
||||||
|
{#each categories as category}
|
||||||
|
<div class="category">
|
||||||
|
<div class="heading">{category.label}</div>
|
||||||
|
<div class="colors">
|
||||||
|
{#each category.colors as color}
|
||||||
|
<div
|
||||||
|
on:click={() => {
|
||||||
|
onChange(`var(--spectrum-global-color-static-${color})`)
|
||||||
|
}}
|
||||||
|
class="color"
|
||||||
|
style="background: var(--spectrum-global-color-static-{color}); color: {checkColor};"
|
||||||
|
title={prettyPrint(color)}
|
||||||
|
>
|
||||||
|
{#if value === `var(--spectrum-global-color-static-${color})`}
|
||||||
|
<Icon name="Checkmark" size="S" />
|
||||||
|
{/if}
|
||||||
|
</div>
|
||||||
|
{/each}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{/each}
|
||||||
|
<div class="category category--custom">
|
||||||
|
<div class="heading">Custom</div>
|
||||||
|
<div class="custom">
|
||||||
|
<Input
|
||||||
|
updateOnChange={false}
|
||||||
|
quiet
|
||||||
|
placeholder="Hex, RGB, HSL..."
|
||||||
|
value={customValue}
|
||||||
|
on:change
|
||||||
|
/>
|
||||||
|
<Icon size="S" name="Close" hoverable on:click={() => onChange(null)} />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{/if}
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.preview {
|
||||||
|
width: 32px;
|
||||||
|
height: 32px;
|
||||||
|
border-radius: 100%;
|
||||||
|
transition: border-color 130ms ease-in-out;
|
||||||
|
box-shadow: 0 0 0 1px var(--spectrum-global-color-gray-300);
|
||||||
|
}
|
||||||
|
.preview:hover {
|
||||||
|
cursor: pointer;
|
||||||
|
box-shadow: 0 0 2px 2px var(--spectrum-global-color-gray-300);
|
||||||
|
}
|
||||||
|
.spectrum-Popover {
|
||||||
|
width: 100%;
|
||||||
|
z-index: 999;
|
||||||
|
top: 100%;
|
||||||
|
padding: var(--spacing-l) var(--spacing-xl);
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
justify-content: flex-start;
|
||||||
|
align-items: stretch;
|
||||||
|
gap: var(--spacing-xl);
|
||||||
|
}
|
||||||
|
.colors {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr 1fr 1fr 1fr 1fr 1fr 1fr 1fr;
|
||||||
|
gap: var(--spacing-xs);
|
||||||
|
}
|
||||||
|
.heading {
|
||||||
|
font-size: var(--font-size-s);
|
||||||
|
font-weight: 600;
|
||||||
|
letter-spacing: 0.14px;
|
||||||
|
flex: 1 1 auto;
|
||||||
|
text-transform: uppercase;
|
||||||
|
grid-column: 1 / 5;
|
||||||
|
margin-bottom: var(--spacing-s);
|
||||||
|
}
|
||||||
|
.color {
|
||||||
|
height: 16px;
|
||||||
|
width: 16px;
|
||||||
|
border-radius: 100%;
|
||||||
|
box-shadow: 0 0 0 1px var(--spectrum-global-color-gray-300);
|
||||||
|
display: grid;
|
||||||
|
place-items: center;
|
||||||
|
}
|
||||||
|
.color:hover {
|
||||||
|
cursor: pointer;
|
||||||
|
box-shadow: 0 0 2px 2px var(--spectrum-global-color-gray-300);
|
||||||
|
}
|
||||||
|
.custom {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr auto;
|
||||||
|
align-items: center;
|
||||||
|
gap: var(--spacing-m);
|
||||||
|
margin-right: var(--spacing-xs);
|
||||||
|
}
|
||||||
|
.category--custom .heading {
|
||||||
|
margin-bottom: var(--spacing-xs);
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -10,6 +10,7 @@
|
||||||
export let id = null
|
export let id = null
|
||||||
export let readonly = false
|
export let readonly = false
|
||||||
export let updateOnChange = true
|
export let updateOnChange = true
|
||||||
|
export let quiet = false
|
||||||
|
|
||||||
const dispatch = createEventDispatcher()
|
const dispatch = createEventDispatcher()
|
||||||
let focus = false
|
let focus = false
|
||||||
|
@ -59,6 +60,7 @@
|
||||||
|
|
||||||
<div
|
<div
|
||||||
class="spectrum-Textfield"
|
class="spectrum-Textfield"
|
||||||
|
class:spectrum-Textfield--quiet={quiet}
|
||||||
class:is-invalid={!!error}
|
class:is-invalid={!!error}
|
||||||
class:is-disabled={disabled}
|
class:is-disabled={disabled}
|
||||||
class:is-focused={focus}
|
class:is-focused={focus}
|
||||||
|
|
|
@ -12,6 +12,7 @@
|
||||||
export let readonly = false
|
export let readonly = false
|
||||||
export let error = null
|
export let error = null
|
||||||
export let updateOnChange = true
|
export let updateOnChange = true
|
||||||
|
export let quiet = false
|
||||||
|
|
||||||
const dispatch = createEventDispatcher()
|
const dispatch = createEventDispatcher()
|
||||||
const onChange = e => {
|
const onChange = e => {
|
||||||
|
@ -29,6 +30,7 @@
|
||||||
{value}
|
{value}
|
||||||
{placeholder}
|
{placeholder}
|
||||||
{type}
|
{type}
|
||||||
|
{quiet}
|
||||||
on:change={onChange}
|
on:change={onChange}
|
||||||
on:click
|
on:click
|
||||||
on:input
|
on:input
|
||||||
|
|
|
@ -55,6 +55,7 @@ export { default as Search } from "./Form/Search.svelte"
|
||||||
export { default as Pagination } from "./Pagination/Pagination.svelte"
|
export { default as Pagination } from "./Pagination/Pagination.svelte"
|
||||||
export { default as Badge } from "./Badge/Badge.svelte"
|
export { default as Badge } from "./Badge/Badge.svelte"
|
||||||
export { default as StatusLight } from "./StatusLight/StatusLight.svelte"
|
export { default as StatusLight } from "./StatusLight/StatusLight.svelte"
|
||||||
|
export { default as ColorPicker } from "./ColorPicker/ColorPicker.svelte"
|
||||||
|
|
||||||
// Typography
|
// Typography
|
||||||
export { default as Body } from "./Typography/Body.svelte"
|
export { default as Body } from "./Typography/Body.svelte"
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
import { Input, Select } from "@budibase/bbui"
|
import { Input, Select, ColorPicker } from "@budibase/bbui"
|
||||||
import FlatButtonGroup from "./PropertyControls/FlatButtonGroup"
|
import FlatButtonGroup from "./PropertyControls/FlatButtonGroup"
|
||||||
import Colorpicker from "./PropertyControls/ColorPicker.svelte"
|
// import Colorpicker from "./PropertyControls/ColorPicker.svelte"
|
||||||
|
|
||||||
export const layout = [
|
export const layout = [
|
||||||
{
|
{
|
||||||
|
@ -274,61 +274,6 @@ export const size = {
|
||||||
],
|
],
|
||||||
}
|
}
|
||||||
|
|
||||||
export const position = [
|
|
||||||
{
|
|
||||||
label: "Position",
|
|
||||||
key: "position",
|
|
||||||
control: Select,
|
|
||||||
options: [
|
|
||||||
{ label: "Static", value: "static" },
|
|
||||||
{ label: "Relative", value: "relative" },
|
|
||||||
{ label: "Fixed", value: "fixed" },
|
|
||||||
{ label: "Absolute", value: "absolute" },
|
|
||||||
{ label: "Sticky", value: "sticky" },
|
|
||||||
],
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: "Top",
|
|
||||||
key: "top",
|
|
||||||
control: Input,
|
|
||||||
placeholder: "px",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: "Right",
|
|
||||||
key: "right",
|
|
||||||
control: Input,
|
|
||||||
placeholder: "px",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: "Bottom",
|
|
||||||
key: "bottom",
|
|
||||||
control: Input,
|
|
||||||
placeholder: "px",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: "Left",
|
|
||||||
key: "left",
|
|
||||||
control: Input,
|
|
||||||
placeholder: "px",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
label: "Z-index",
|
|
||||||
key: "z-index",
|
|
||||||
control: Select,
|
|
||||||
options: [
|
|
||||||
{ label: "-9999", value: "-9999" },
|
|
||||||
{ label: "-3", value: "-3" },
|
|
||||||
{ label: "-2", value: "-2" },
|
|
||||||
{ label: "-1", value: "-1" },
|
|
||||||
{ label: "0", value: "0" },
|
|
||||||
{ label: "1", value: "1" },
|
|
||||||
{ label: "2", value: "2" },
|
|
||||||
{ label: "3", value: "3" },
|
|
||||||
{ label: "9999", value: "9999" },
|
|
||||||
],
|
|
||||||
},
|
|
||||||
]
|
|
||||||
|
|
||||||
export const typography = [
|
export const typography = [
|
||||||
{
|
{
|
||||||
label: "Font",
|
label: "Font",
|
||||||
|
@ -401,7 +346,7 @@ export const typography = [
|
||||||
{
|
{
|
||||||
label: "Color",
|
label: "Color",
|
||||||
key: "color",
|
key: "color",
|
||||||
control: Colorpicker,
|
control: ColorPicker,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: "align",
|
label: "align",
|
||||||
|
@ -445,14 +390,13 @@ export const background = {
|
||||||
{
|
{
|
||||||
label: "Color",
|
label: "Color",
|
||||||
key: "background",
|
key: "background",
|
||||||
control: Colorpicker,
|
control: ColorPicker,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: "Gradient",
|
label: "Gradient",
|
||||||
key: "background-image",
|
key: "background-image",
|
||||||
control: Select,
|
control: Select,
|
||||||
options: [
|
options: [
|
||||||
{ label: "None", value: "none" },
|
|
||||||
{
|
{
|
||||||
label: "Warm Flame",
|
label: "Warm Flame",
|
||||||
value:
|
value:
|
||||||
|
@ -534,21 +478,17 @@ export const border = {
|
||||||
{
|
{
|
||||||
label: "Color",
|
label: "Color",
|
||||||
key: "border-color",
|
key: "border-color",
|
||||||
control: Colorpicker,
|
control: ColorPicker,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: "Radius",
|
label: "Radius",
|
||||||
key: "border-radius",
|
key: "border-radius",
|
||||||
control: Select,
|
control: Select,
|
||||||
options: [
|
options: [
|
||||||
{ label: "None", value: "0" },
|
|
||||||
{ label: "X Small", value: "0.125rem" },
|
|
||||||
{ label: "Small", value: "0.25rem" },
|
{ label: "Small", value: "0.25rem" },
|
||||||
{ label: "Medium", value: "0.5rem" },
|
{ label: "Medium", value: "0.5rem" },
|
||||||
{ label: "Large", value: "1rem" },
|
{ label: "Large", value: "1rem" },
|
||||||
{ label: "X Large", value: "2rem" },
|
{ label: "Round", value: "100%" },
|
||||||
{ label: "XX Large", value: "4rem" },
|
|
||||||
{ label: "Round", value: "5678px" },
|
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -556,12 +496,9 @@ export const border = {
|
||||||
key: "border-width",
|
key: "border-width",
|
||||||
control: Select,
|
control: Select,
|
||||||
options: [
|
options: [
|
||||||
{ label: "None", value: "0" },
|
|
||||||
{ label: "X Small", value: "0.5px" },
|
|
||||||
{ label: "Small", value: "1px" },
|
{ label: "Small", value: "1px" },
|
||||||
{ label: "Medium", value: "2px" },
|
{ label: "Medium", value: "2px" },
|
||||||
{ label: "Large", value: "4px" },
|
{ label: "Large", value: "4px" },
|
||||||
{ label: "X large", value: "8px" },
|
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -569,8 +506,6 @@ export const border = {
|
||||||
key: "box-shadow",
|
key: "box-shadow",
|
||||||
control: Select,
|
control: Select,
|
||||||
options: [
|
options: [
|
||||||
{ label: "None", value: "none" },
|
|
||||||
{ label: "X Small", value: "0 1px 2px 0 rgba(0, 0, 0, 0.05)" },
|
|
||||||
{
|
{
|
||||||
label: "Small",
|
label: "Small",
|
||||||
value:
|
value:
|
||||||
|
@ -584,12 +519,7 @@ export const border = {
|
||||||
{
|
{
|
||||||
label: "Large",
|
label: "Large",
|
||||||
value:
|
value:
|
||||||
"0 10px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05)",
|
"0 8px 15px -3px rgba(0, 0, 0, 0.1), 0 4px 6px -2px rgba(0, 0, 0, 0.05)",
|
||||||
},
|
|
||||||
{
|
|
||||||
label: "X Large",
|
|
||||||
value:
|
|
||||||
"0 20px 25px -5px rgba(0, 0, 0, 0.1), 0 10px 10px -5px rgba(0, 0, 0, 0.04)",
|
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
|
Loading…
Reference in New Issue