Merge branch 'workflow-v1' of github.com:Budibase/budibase into workflow-v1
After Width: | Height: | Size: 109 KiB |
|
@ -0,0 +1,31 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<!-- Generator: Adobe Illustrator 24.1.2, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
|
||||||
|
<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
|
||||||
|
viewBox="0 0 128 128" style="enable-background:new 0 0 128 128;" xml:space="preserve">
|
||||||
|
<style type="text/css">
|
||||||
|
.st0{fill:#393C44;}
|
||||||
|
.st1{fill:#FFFFFF;}
|
||||||
|
</style>
|
||||||
|
<g>
|
||||||
|
<path class="st0" d="M117.33,128H10.67C4.78,128,0,123.22,0,117.33V10.67C0,4.78,4.78,0,10.67,0h106.67
|
||||||
|
C123.22,0,128,4.78,128,10.67v106.67C128,123.22,123.22,128,117.33,128z"/>
|
||||||
|
<g>
|
||||||
|
<path class="st1" d="M75.94,32v27.84c3.14-3.38,7.07-5.07,11.79-5.07c2.8,0,5.37,0.54,7.7,1.63c2.33,1.09,4.32,2.55,5.97,4.39
|
||||||
|
c1.65,1.84,2.93,4.01,3.87,6.51c0.93,2.5,1.4,5.16,1.4,7.98c0,2.87-0.48,5.57-1.44,8.09c-0.96,2.52-2.3,4.72-4.02,6.58
|
||||||
|
c-1.72,1.87-3.75,3.34-6.08,4.43C92.8,95.46,90.28,96,87.58,96c-4.91,0-8.79-1.84-11.64-5.52v4.31H62.6V32H75.94z M92.74,75.5
|
||||||
|
c0-1.21-0.22-2.36-0.66-3.44c-0.44-1.08-1.06-2.03-1.84-2.84c-0.79-0.81-1.7-1.45-2.73-1.93c-1.03-0.48-2.16-0.72-3.39-0.72
|
||||||
|
c-1.18,0-2.28,0.23-3.32,0.68c-1.03,0.45-1.93,1.09-2.69,1.89c-0.76,0.81-1.38,1.75-1.84,2.84c-0.47,1.09-0.7,2.23-0.7,3.44
|
||||||
|
s0.22,2.34,0.66,3.4c0.44,1.06,1.06,1.98,1.84,2.76c0.79,0.78,1.71,1.41,2.76,1.89c1.06,0.48,2.17,0.72,3.35,0.72
|
||||||
|
c1.18,0,2.28-0.23,3.32-0.68c1.03-0.45,1.93-1.08,2.69-1.89c0.76-0.81,1.37-1.74,1.84-2.8C92.51,77.77,92.74,76.66,92.74,75.5z"/>
|
||||||
|
</g>
|
||||||
|
<g>
|
||||||
|
<path class="st1" d="M34.67,32v27.84c3.14-3.38,7.07-5.07,11.79-5.07c2.8,0,5.37,0.54,7.7,1.63c2.33,1.09,4.32,2.55,5.97,4.39
|
||||||
|
c1.65,1.84,2.93,4.01,3.87,6.51c0.93,2.5,1.4,5.16,1.4,7.98c0,2.87-0.48,5.57-1.44,8.09c-0.96,2.52-2.3,4.72-4.02,6.58
|
||||||
|
c-1.72,1.87-3.75,3.34-6.08,4.43C51.53,95.46,49.01,96,46.31,96c-4.91,0-8.79-1.84-11.64-5.52v4.31H21.33V32H34.67z M51.47,75.5
|
||||||
|
c0-1.21-0.22-2.36-0.66-3.44c-0.44-1.08-1.06-2.03-1.84-2.84c-0.79-0.81-1.7-1.45-2.73-1.93c-1.03-0.48-2.16-0.72-3.39-0.72
|
||||||
|
c-1.18,0-2.28,0.23-3.32,0.68c-1.03,0.45-1.93,1.09-2.69,1.89c-0.76,0.81-1.38,1.75-1.84,2.84c-0.47,1.09-0.7,2.23-0.7,3.44
|
||||||
|
s0.22,2.34,0.66,3.4c0.44,1.06,1.06,1.98,1.84,2.76c0.79,0.78,1.71,1.41,2.76,1.89c1.06,0.48,2.17,0.72,3.35,0.72
|
||||||
|
c1.18,0,2.28-0.23,3.32-0.68c1.03-0.45,1.93-1.08,2.69-1.89c0.76-0.81,1.37-1.74,1.84-2.8C51.24,77.77,51.47,76.66,51.47,75.5z"/>
|
||||||
|
</g>
|
||||||
|
</g>
|
||||||
|
</svg>
|
After Width: | Height: | Size: 2.3 KiB |
|
@ -1,142 +1,54 @@
|
||||||
import { pipe } from "components/common/core"
|
export const generate_screen_css = component_arr => {
|
||||||
import { filter, map, reduce, toPairs } from "lodash/fp"
|
|
||||||
|
|
||||||
const self = n => n
|
|
||||||
const join_with = delimiter => a => a.join(delimiter)
|
|
||||||
const empty_string_to_unset = s => (s.length ? s : "0")
|
|
||||||
const add_suffix_if_number = suffix => s => {
|
|
||||||
try {
|
|
||||||
if (isNaN(s) || isNaN(parseFloat(s))) return s
|
|
||||||
} catch (_) {
|
|
||||||
return s
|
|
||||||
}
|
|
||||||
return s + suffix
|
|
||||||
}
|
|
||||||
|
|
||||||
export const make_margin = values =>
|
|
||||||
pipe(values, [
|
|
||||||
map(empty_string_to_unset),
|
|
||||||
map(add_suffix_if_number("px")),
|
|
||||||
join_with(" "),
|
|
||||||
])
|
|
||||||
|
|
||||||
const css_map = {
|
|
||||||
templaterows: {
|
|
||||||
name: "grid-template-rows",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
templatecolumns: {
|
|
||||||
name: "grid-template-columns",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
align: {
|
|
||||||
name: "align-items",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
justify: {
|
|
||||||
name: "justify-content",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
direction: {
|
|
||||||
name: "flex-direction",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
gridarea: {
|
|
||||||
name: "grid-area",
|
|
||||||
generate: make_margin,
|
|
||||||
},
|
|
||||||
gap: {
|
|
||||||
name: "grid-gap",
|
|
||||||
generate: n => `${n}px`,
|
|
||||||
},
|
|
||||||
columnstart: {
|
|
||||||
name: "grid-column-start",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
columnend: {
|
|
||||||
name: "grid-column-end",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
rowstart: {
|
|
||||||
name: "grid-row-start",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
rowend: {
|
|
||||||
name: "grid-row-end",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
padding: {
|
|
||||||
name: "padding",
|
|
||||||
generate: make_margin,
|
|
||||||
},
|
|
||||||
margin: {
|
|
||||||
name: "margin",
|
|
||||||
generate: make_margin,
|
|
||||||
},
|
|
||||||
zindex: {
|
|
||||||
name: "z-index",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
height: {
|
|
||||||
name: "height",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
width: {
|
|
||||||
name: "width",
|
|
||||||
generate: self,
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
export const generate_rule = ([name, values]) =>
|
|
||||||
`${css_map[name].name}: ${css_map[name].generate(values)};`
|
|
||||||
|
|
||||||
const handle_grid = (acc, [name, value]) => {
|
|
||||||
let tmp = []
|
|
||||||
|
|
||||||
if (name === "row" || name === "column") {
|
|
||||||
if (value[0]) tmp.push([`${name}start`, value[0]])
|
|
||||||
if (value[1]) tmp.push([`${name}end`, value[1]])
|
|
||||||
return acc.concat(tmp)
|
|
||||||
}
|
|
||||||
|
|
||||||
return acc.concat([[name, value]])
|
|
||||||
}
|
|
||||||
|
|
||||||
const object_to_css_string = [
|
|
||||||
toPairs,
|
|
||||||
reduce(handle_grid, []),
|
|
||||||
filter(v => (Array.isArray(v[1]) ? v[1].some(s => s.length) : v[1].length)),
|
|
||||||
map(generate_rule),
|
|
||||||
join_with("\n"),
|
|
||||||
]
|
|
||||||
|
|
||||||
export const generate_css = ({ layout, position }) => {
|
|
||||||
let _layout = pipe(layout, object_to_css_string)
|
|
||||||
if (_layout.length) {
|
|
||||||
_layout += `\ndisplay: ${_layout.includes("flex") ? "flex" : "grid"};`
|
|
||||||
}
|
|
||||||
|
|
||||||
return {
|
|
||||||
layout: _layout,
|
|
||||||
position: pipe(position, object_to_css_string),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const apply_class = (id, name, styles) => `.${name}-${id} {\n${styles}\n}`
|
|
||||||
|
|
||||||
export const generate_screen_css = component_array => {
|
|
||||||
let styles = ""
|
let styles = ""
|
||||||
let emptyStyles = { layout: {}, position: {} }
|
for (const { _styles, _id, _children, _component } of component_arr) {
|
||||||
|
let [componentName] = _component.match(/[a-z]*$/)
|
||||||
for (let i = 0; i < component_array.length; i += 1) {
|
Object.keys(_styles).forEach(selector => {
|
||||||
const { _styles, _id, _children } = component_array[i]
|
const cssString = generate_css(_styles[selector])
|
||||||
const { layout, position } = generate_css(_styles || emptyStyles)
|
if (cssString) {
|
||||||
|
styles += apply_class(_id, componentName, cssString, selector)
|
||||||
styles += apply_class(_id, "pos", position) + "\n"
|
}
|
||||||
styles += apply_class(_id, "lay", layout) + "\n"
|
})
|
||||||
if (_children && _children.length) {
|
if (_children && _children.length) {
|
||||||
styles += generate_screen_css(_children) + "\n"
|
styles += generate_screen_css(_children) + "\n"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return styles.trim()
|
return styles.trim()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export const generate_css = style => {
|
||||||
|
let cssString = Object.entries(style).reduce((str, [key, value]) => {
|
||||||
|
//TODO Handle arrays and objects here also
|
||||||
|
if (typeof value === "string") {
|
||||||
|
if (value) {
|
||||||
|
return (str += `${key}: ${value};\n`)
|
||||||
|
}
|
||||||
|
} else if (Array.isArray(value)) {
|
||||||
|
if (value.length > 0 && !value.every(v => v === "")) {
|
||||||
|
return (str += `${key}: ${value
|
||||||
|
.map(generate_array_styles)
|
||||||
|
.join(" ")};\n`)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}, "")
|
||||||
|
|
||||||
|
return (cssString || "").trim()
|
||||||
|
}
|
||||||
|
|
||||||
|
export const generate_array_styles = item => {
|
||||||
|
let safeItem = item === "" ? 0 : item
|
||||||
|
let hasPx = new RegExp("px$")
|
||||||
|
if (!hasPx.test(safeItem)) {
|
||||||
|
return `${safeItem}px`
|
||||||
|
} else {
|
||||||
|
return safeItem
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
export const apply_class = (id, name = "element", styles, selector) => {
|
||||||
|
if (selector === "normal") {
|
||||||
|
return `.${name}-${id} {\n${styles}\n}`
|
||||||
|
} else {
|
||||||
|
let sel = selector === "selected" ? "::selection" : `:${selector}`
|
||||||
|
return `.${name}-${id}${sel} {\n${styles}\n}`
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -140,10 +140,11 @@ const _saveScreen = async (store, s, screen) => {
|
||||||
return s
|
return s
|
||||||
}
|
}
|
||||||
|
|
||||||
const _saveScreenApi = (screen, s) =>
|
const _saveScreenApi = (screen, s) => {
|
||||||
api
|
api
|
||||||
.post(`/_builder/api/${s.appId}/pages/${s.currentPageName}/screen`, screen)
|
.post(`/_builder/api/${s.appId}/pages/${s.currentPageName}/screen`, screen)
|
||||||
.then(() => _savePage(s))
|
.then(() => _savePage(s))
|
||||||
|
}
|
||||||
|
|
||||||
const createScreen = store => (screenName, route, layoutComponentName) => {
|
const createScreen = store => (screenName, route, layoutComponentName) => {
|
||||||
store.update(state => {
|
store.update(state => {
|
||||||
|
@ -278,7 +279,6 @@ const removeStylesheet = store => stylesheet => {
|
||||||
|
|
||||||
const _savePage = async s => {
|
const _savePage = async s => {
|
||||||
const page = s.pages[s.currentPageName]
|
const page = s.pages[s.currentPageName]
|
||||||
|
|
||||||
await api.post(`/_builder/api/${s.appId}/pages/${s.currentPageName}`, {
|
await api.post(`/_builder/api/${s.appId}/pages/${s.currentPageName}`, {
|
||||||
page: { componentLibraries: s.pages.componentLibraries, ...page },
|
page: { componentLibraries: s.pages.componentLibraries, ...page },
|
||||||
uiFunctions: s.currentPageFunctions,
|
uiFunctions: s.currentPageFunctions,
|
||||||
|
@ -427,6 +427,7 @@ const setComponentStyle = store => (type, name, value) => {
|
||||||
state.currentComponentInfo._styles = {}
|
state.currentComponentInfo._styles = {}
|
||||||
}
|
}
|
||||||
state.currentComponentInfo._styles[type][name] = value
|
state.currentComponentInfo._styles[type][name] = value
|
||||||
|
|
||||||
state.currentPreviewItem._css = generate_screen_css([
|
state.currentPreviewItem._css = generate_screen_css([
|
||||||
state.currentPreviewItem.props,
|
state.currentPreviewItem.props,
|
||||||
])
|
])
|
||||||
|
|
|
@ -36,6 +36,7 @@ const workflowActions = store => ({
|
||||||
select: workflow => {
|
select: workflow => {
|
||||||
store.update(state => {
|
store.update(state => {
|
||||||
state.selectedWorkflowId = workflow._id
|
state.selectedWorkflowId = workflow._id
|
||||||
|
state.selectedWorkflowBlock = null
|
||||||
return state;
|
return state;
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,13 +1,78 @@
|
||||||
<script>
|
<script>
|
||||||
import { onMount, beforeUpdate, afterUpdate } from "svelte"
|
import { onMount } from "svelte"
|
||||||
|
// import { HsvPicker } from "svelte-color-picker"
|
||||||
|
|
||||||
export let value = null
|
// export let initialValue = "#ffffff"
|
||||||
export let onChanged = () => {}
|
export let onChange = color => {}
|
||||||
export let swatches = []
|
export let open = false
|
||||||
|
let value = "#ffffff"
|
||||||
|
|
||||||
let picker
|
let _justMounted = true //see onColorChange
|
||||||
let cp = null
|
let pickerHeight = 275
|
||||||
|
let colorPreview
|
||||||
|
let pickerTopPosition = null
|
||||||
|
|
||||||
|
function rbgaToHexa({ r, g, b, a }) {
|
||||||
|
r = r.toString(16)
|
||||||
|
g = g.toString(16)
|
||||||
|
b = b.toString(16)
|
||||||
|
a = Math.round(a * 255).toString(16)
|
||||||
|
|
||||||
|
if (r.length == 1) r = "0" + r
|
||||||
|
if (g.length == 1) g = "0" + g
|
||||||
|
if (b.length == 1) b = "0" + b
|
||||||
|
if (a.length == 1) a = "0" + a
|
||||||
|
|
||||||
|
return "#" + r + g + b + a
|
||||||
|
}
|
||||||
|
|
||||||
|
function onColourChange(rgba) {
|
||||||
|
value = rbgaToHexa(rgba.detail)
|
||||||
|
|
||||||
|
//Hack: so that color change doesn't fire onMount
|
||||||
|
if (!_justMounted) {
|
||||||
|
// onChange(value)
|
||||||
|
}
|
||||||
|
_justMounted = false
|
||||||
|
}
|
||||||
|
|
||||||
|
function toggleColorpicker(isOpen) {
|
||||||
|
if (isOpen) {
|
||||||
|
const {
|
||||||
|
y: previewYPosition,
|
||||||
|
height: previewHeight,
|
||||||
|
} = colorPreview.getBoundingClientRect()
|
||||||
|
|
||||||
|
let wiggleRoom = window.innerHeight - previewYPosition
|
||||||
|
let displayTop = wiggleRoom < pickerHeight
|
||||||
|
|
||||||
|
if (displayTop) {
|
||||||
|
pickerTopPosition = previewYPosition - (pickerHeight - window.scrollY)
|
||||||
|
} else {
|
||||||
|
pickerTopPosition = null
|
||||||
|
}
|
||||||
|
}
|
||||||
|
open = isOpen
|
||||||
|
}
|
||||||
|
|
||||||
|
$: style = open ? "display: block;" : "display: none;"
|
||||||
|
$: pickerStyle = pickerTopPosition ? `top: ${pickerTopPosition}px;` : ""
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div
|
||||||
|
bind:this={colorPreview}
|
||||||
|
on:click={() => toggleColorpicker(true)}
|
||||||
|
class="color-preview"
|
||||||
|
style={`background: ${value}`} />
|
||||||
|
|
||||||
|
<div class="colorpicker" {style}>
|
||||||
|
<div class="overlay" on:click|self={() => toggleColorpicker(false)} />
|
||||||
|
<div class="cp" style={pickerStyle}>
|
||||||
|
<!-- <HsvPicker on:colorChange={onColourChange} startColor={value} /> -->
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<!--
|
||||||
|
OLD LOCAL STORAGE OPTIONS. INCLUDING FOR ADDING LATER
|
||||||
function getRecentColors() {
|
function getRecentColors() {
|
||||||
let colorStore = localStorage.getItem("bb:recentColors")
|
let colorStore = localStorage.getItem("bb:recentColors")
|
||||||
if (!!colorStore) {
|
if (!!colorStore) {
|
||||||
|
@ -25,47 +90,27 @@
|
||||||
picker.addSwatch(color)
|
picker.addSwatch(color)
|
||||||
localStorage.setItem("bb:recentColors", JSON.stringify(swatches))
|
localStorage.setItem("bb:recentColors", JSON.stringify(swatches))
|
||||||
}
|
}
|
||||||
|
} -->
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.overlay {
|
||||||
|
position: absolute;
|
||||||
|
top: 0;
|
||||||
|
left: 0;
|
||||||
|
right: 0;
|
||||||
|
bottom: 0;
|
||||||
|
/* background: rgba(5, 5, 5, 0.25); */
|
||||||
}
|
}
|
||||||
|
|
||||||
function createPicker() {
|
.cp {
|
||||||
picker = Pickr.create({
|
position: absolute;
|
||||||
el: cp,
|
right: 25px;
|
||||||
theme: "nano",
|
|
||||||
default: value || "#000000",
|
|
||||||
|
|
||||||
swatches,
|
|
||||||
closeWithKey: "Escape",
|
|
||||||
|
|
||||||
components: {
|
|
||||||
preview: true,
|
|
||||||
opacity: true,
|
|
||||||
hue: true,
|
|
||||||
|
|
||||||
interaction: {
|
|
||||||
hex: true,
|
|
||||||
rgba: true,
|
|
||||||
input: true,
|
|
||||||
save: true,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
})
|
|
||||||
}
|
}
|
||||||
|
.color-preview {
|
||||||
afterUpdate(() => {
|
height: 30px;
|
||||||
picker.setColor(value)
|
width: 100%;
|
||||||
})
|
margin: 5px;
|
||||||
|
cursor: pointer;
|
||||||
onMount(() => {
|
border: 1px solid gainsboro;
|
||||||
getRecentColors()
|
}
|
||||||
createPicker()
|
</style>
|
||||||
|
|
||||||
picker.on("save", (colour, instance) => {
|
|
||||||
let color = colour.toHEXA().toString()
|
|
||||||
onChanged(color)
|
|
||||||
setRecentColor(color)
|
|
||||||
picker.hide()
|
|
||||||
})
|
|
||||||
})
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<div bind:this={cp} class="color-picker" />
|
|
||||||
|
|
|
@ -0,0 +1,12 @@
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
width="24"
|
||||||
|
height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path
|
||||||
|
d="M7 11.5a4.5 4.5 0 1 1 0-9 4.5 4.5 0 0 1 0 9zm0 10a4.5 4.5 0 1 1 0-9 4.5
|
||||||
|
4.5 0 0 1 0 9zm10-10a4.5 4.5 0 1 1 0-9 4.5 4.5 0 0 1 0 9zm0 10a4.5 4.5 0 1 1
|
||||||
|
0-9 4.5 4.5 0 0 1 0 9z"
|
||||||
|
fill="rgba(128,129,146,1)" />
|
||||||
|
</svg>
|
After Width: | Height: | Size: 370 B |
|
@ -0,0 +1,15 @@
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
width="24"
|
||||||
|
height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path
|
||||||
|
d="M5.07 16A7.06 7.06 0 0 1 5
|
||||||
|
15v-1H3v-2h2v-1c0-.34.024-.673.07-1H3V8h2.674a7.03 7.03 0 0 1
|
||||||
|
2.84-3.072l-1.05-1.05L8.88 2.465l1.683 1.684a7.03 7.03 0 0 1 2.876
|
||||||
|
0l1.683-1.684 1.415 1.415-1.05 1.05A7.03 7.03 0 0 1 18.326
|
||||||
|
8H21v2h-2.07c.046.327.07.66.07 1v1h2v2h-2v1c0 .34-.024.673-.07
|
||||||
|
1H21v2h-2.674a7 7 0 0 1-12.652 0H3v-2h2.07zM9 10v2h6v-2H9zm0 4v2h6v-2H9z"
|
||||||
|
fill="rgba(128,129,146,1)" />
|
||||||
|
</svg>
|
After Width: | Height: | Size: 561 B |
|
@ -0,0 +1,14 @@
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
width="24"
|
||||||
|
height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path
|
||||||
|
d="M12 11a5 5 0 0 1 5 5v6H7v-6a5 5 0 0 1 5-5zm-6.712 3.006a6.983 6.983 0 0
|
||||||
|
0-.28 1.65L5 16v6H2v-4.5a3.5 3.5 0 0 1 3.119-3.48l.17-.014zm13.424 0A3.501
|
||||||
|
3.501 0 0 1 22 17.5V22h-3v-6c0-.693-.1-1.362-.288-1.994zM5.5 8a2.5 2.5 0 1 1
|
||||||
|
0 5 2.5 2.5 0 0 1 0-5zm13 0a2.5 2.5 0 1 1 0 5 2.5 2.5 0 0 1 0-5zM12 2a4 4 0
|
||||||
|
1 1 0 8 4 4 0 0 1 0-8z"
|
||||||
|
fill="rgba(128,129,146,1)" />
|
||||||
|
</svg>
|
After Width: | Height: | Size: 529 B |
|
@ -0,0 +1,14 @@
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
width="24"
|
||||||
|
height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path
|
||||||
|
d="M14.121 10.48a1 1 0 0 0-1.414 0l-.707.706a2 2 0 1
|
||||||
|
1-2.828-2.828l5.63-5.632a6.5 6.5 0 0 1 6.377 10.568l-2.108
|
||||||
|
2.135-4.95-4.95zM3.161 4.468a6.503 6.503 0 0 1 8.009-.938L7.757 6.944a4 4 0
|
||||||
|
0 0 5.513 5.794l.144-.137 4.243 4.242-4.243 4.243a2 2 0 0 1-2.828 0L3.16
|
||||||
|
13.66a6.5 6.5 0 0 1 0-9.192z"
|
||||||
|
fill="rgba(128,129,146,1)" />
|
||||||
|
</svg>
|
After Width: | Height: | Size: 493 B |
|
@ -0,0 +1,11 @@
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
width="24"
|
||||||
|
height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path
|
||||||
|
d="M20 22H4a1 1 0 0 1-1-1V3a1 1 0 0 1 1-1h16a1 1 0 0 1 1 1v18a1 1 0 0 1-1
|
||||||
|
1zM8 7v2h8V7H8zm0 4v2h8v-2H8zm0 4v2h5v-2H8z"
|
||||||
|
fill="rgba(128,129,146,1)" />
|
||||||
|
</svg>
|
After Width: | Height: | Size: 309 B |
|
@ -0,0 +1,12 @@
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
width="24"
|
||||||
|
height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path
|
||||||
|
d="M3 3h18a1 1 0 0 1 1 1v16a1 1 0 0 1-1 1H3a1 1 0 0 1-1-1V4a1 1 0 0 1
|
||||||
|
1-1zm9.06 8.683L5.648 6.238 4.353 7.762l7.72 6.555
|
||||||
|
7.581-6.56-1.308-1.513-6.285 5.439z"
|
||||||
|
fill="rgba(128,129,146,1)" />
|
||||||
|
</svg>
|
After Width: | Height: | Size: 352 B |
|
@ -0,0 +1,11 @@
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
width="24"
|
||||||
|
height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path
|
||||||
|
d="M7 20.981a6.5 6.5 0 0 1-2.936-12 8.001 8.001 0 0 1 15.872 0 6.5 6.5 0 0
|
||||||
|
1-2.936 12V21H7v-.019zM13 13h3l-4-5-4 5h3v4h2v-4z"
|
||||||
|
fill="rgba(128,129,146,1)" />
|
||||||
|
</svg>
|
After Width: | Height: | Size: 316 B |
|
@ -0,0 +1,11 @@
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
width="24"
|
||||||
|
height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path
|
||||||
|
d="M13 16.938V19h5v2H6v-2h5v-2.062A8.001 8.001 0 0 1 4 9V3h16v6a8.001 8.001
|
||||||
|
0 0 1-7 7.938zM1 5h2v4H1V5zm20 0h2v4h-2V5z"
|
||||||
|
fill="rgba(128,129,146,1)" />
|
||||||
|
</svg>
|
After Width: | Height: | Size: 310 B |
|
@ -0,0 +1,16 @@
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
width="24"
|
||||||
|
height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path
|
||||||
|
d="M22.162 5.656a8.384 8.384 0 0 1-2.402.658A4.196 4.196 0 0 0 21.6
|
||||||
|
4c-.82.488-1.719.83-2.656 1.015a4.182 4.182 0 0 0-7.126 3.814 11.874 11.874
|
||||||
|
0 0 1-8.62-4.37 4.168 4.168 0 0 0-.566 2.103c0 1.45.738 2.731 1.86
|
||||||
|
3.481a4.168 4.168 0 0 1-1.894-.523v.052a4.185 4.185 0 0 0 3.355 4.101 4.21
|
||||||
|
4.21 0 0 1-1.89.072A4.185 4.185 0 0 0 7.97 16.65a8.394 8.394 0 0 1-6.191
|
||||||
|
1.732 11.83 11.83 0 0 0 6.41 1.88c7.693 0 11.9-6.373 11.9-11.9
|
||||||
|
0-.18-.005-.362-.013-.54a8.496 8.496 0 0 0 2.087-2.165z"
|
||||||
|
fill="rgba(128,129,146,1)" />
|
||||||
|
</svg>
|
After Width: | Height: | Size: 689 B |
|
@ -0,0 +1,13 @@
|
||||||
|
<svg
|
||||||
|
xmlns="http://www.w3.org/2000/svg"
|
||||||
|
viewBox="0 0 24 24"
|
||||||
|
width="24"
|
||||||
|
height="24">
|
||||||
|
<path fill="none" d="M0 0h24v24H0z" />
|
||||||
|
<path
|
||||||
|
d="M12 22C6.477 22 2 17.523 2 12S6.477 2 12 2s10 4.477 10 10-4.477 10-10
|
||||||
|
10zm4.82-4.924A7 7 0 0 0 9.032 5.658l.975 1.755A5 5 0 0 1 17 12h-3l2.82
|
||||||
|
5.076zm-1.852 1.266l-.975-1.755A5 5 0 0 1 7 12h3L7.18 6.924a7 7 0 0 0 7.788
|
||||||
|
11.418z"
|
||||||
|
fill="rgba(128,129,146,1)" />
|
||||||
|
</svg>
|
After Width: | Height: | Size: 428 B |
|
@ -19,3 +19,13 @@ export { default as AddIcon } from "./Add.svelte"
|
||||||
export { default as JavaScriptIcon } from "./JavaScript.svelte"
|
export { default as JavaScriptIcon } from "./JavaScript.svelte"
|
||||||
export { default as PreviewIcon } from "./Preview.svelte"
|
export { default as PreviewIcon } from "./Preview.svelte"
|
||||||
export { default as SettingsIcon } from "./Settings.svelte"
|
export { default as SettingsIcon } from "./Settings.svelte"
|
||||||
|
export { default as AppsIcon } from "./Apps.svelte"
|
||||||
|
export { default as UpdatesIcon } from "./Updates.svelte"
|
||||||
|
export { default as HostingIcon } from "./Hosting.svelte"
|
||||||
|
export { default as DocumentationIcon } from "./Documentation.svelte"
|
||||||
|
export { default as TutorialsIcon } from "./Tutorials.svelte"
|
||||||
|
export { default as CommunityIcon } from "./Community.svelte"
|
||||||
|
export { default as ContributionIcon } from "./Contribution.svelte"
|
||||||
|
export { default as BugIcon } from "./Bug.svelte"
|
||||||
|
export { default as EmailIcon } from "./Email.svelte"
|
||||||
|
export { default as TwitterIcon } from "./Twitter.svelte"
|
||||||
|
|
|
@ -1,19 +1,22 @@
|
||||||
<script>
|
<script>
|
||||||
export let value = ""
|
export let value = ""
|
||||||
|
export let width = ""
|
||||||
|
|
||||||
|
let style = { width }
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<input type="text" on:change bind:value />
|
<input type="text" style={`width: ${width};`} on:change bind:value />
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
input {
|
input {
|
||||||
display: block;
|
display: block;
|
||||||
font-size: 14px;
|
font-size: 14px;
|
||||||
font-family: sans-serif;
|
|
||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
color: #163057;
|
color: var(--ink);
|
||||||
line-height: 1.3;
|
line-height: 1.3;
|
||||||
padding: 1em 2.6em 0.9em 1.4em;
|
padding: 12px;
|
||||||
width: 100%;
|
width: 164px;
|
||||||
|
float: right;
|
||||||
max-width: 100%;
|
max-width: 100%;
|
||||||
box-sizing: border-box;
|
box-sizing: border-box;
|
||||||
margin: 0;
|
margin: 0;
|
||||||
|
@ -21,7 +24,7 @@
|
||||||
-webkit-appearance: none;
|
-webkit-appearance: none;
|
||||||
appearance: none;
|
appearance: none;
|
||||||
background: #fff;
|
background: #fff;
|
||||||
border: 1px solid #ccc;
|
border: 1px solid var(--grey-dark);
|
||||||
height: 35px;
|
height: 32px;
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
|
@ -2,43 +2,58 @@
|
||||||
import { onMount } from "svelte"
|
import { onMount } from "svelte"
|
||||||
|
|
||||||
export let meta = []
|
export let meta = []
|
||||||
export let size = ""
|
export let label = ""
|
||||||
export let values = []
|
export let value = [0, 0, 0, 0]
|
||||||
export let type = "number"
|
export let type = "number"
|
||||||
export let onStyleChanged = () => {}
|
export let onChange = () => {}
|
||||||
|
|
||||||
let _values = values.map(v => v)
|
function handleChange(val, idx) {
|
||||||
|
value.splice(idx, 1, val)
|
||||||
$: onStyleChanged(_values)
|
value = value
|
||||||
|
onChange(value)
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="inputs {size}">
|
<div class="input-container">
|
||||||
|
<div class="label">{label}</div>
|
||||||
|
<div class="inputs">
|
||||||
{#each meta as { placeholder }, i}
|
{#each meta as { placeholder }, i}
|
||||||
<input
|
<input
|
||||||
{type}
|
{type}
|
||||||
{placeholder}
|
placeholder={placeholder || ''}
|
||||||
value={values[i]}
|
value={!value || value[i] === 0 ? '' : value[i]}
|
||||||
on:input={e => (_values[i] = e.target.value)} />
|
on:change={e => handleChange(e.target.value || 0, i)} />
|
||||||
{/each}
|
{/each}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
|
.input-container {
|
||||||
|
}
|
||||||
|
|
||||||
|
.label {
|
||||||
|
flex: 0;
|
||||||
|
}
|
||||||
|
|
||||||
.inputs {
|
.inputs {
|
||||||
display: flex;
|
flex: 1;
|
||||||
justify-content: space-between;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
input {
|
input {
|
||||||
width: 83px;
|
width: 40px;
|
||||||
font-size: 13px;
|
height: 32px;
|
||||||
|
font-size: 12px;
|
||||||
font-weight: 700;
|
font-weight: 700;
|
||||||
color: #163057;
|
margin: 0px 0px 0px 1px;
|
||||||
|
text-align: center;
|
||||||
|
color: var(--ink);
|
||||||
opacity: 0.7;
|
opacity: 0.7;
|
||||||
padding: 5px 10px;
|
padding: 0px 4px;
|
||||||
box-sizing: border-box;
|
box-sizing: border-box;
|
||||||
border: 1px solid #dbdbdb;
|
border: 1px solid var(--grey);
|
||||||
border-radius: 2px;
|
border-radius: 2px;
|
||||||
outline: none;
|
outline: none;
|
||||||
|
float: right;
|
||||||
}
|
}
|
||||||
|
|
||||||
input[type="number"]::-webkit-inner-spin-button,
|
input[type="number"]::-webkit-inner-spin-button,
|
||||||
|
@ -49,17 +64,11 @@
|
||||||
margin: 0;
|
margin: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
.small > input {
|
input[type="number"] {
|
||||||
width: 38px;
|
-moz-appearance: textfield;
|
||||||
height: 38px;
|
|
||||||
display: flex;
|
|
||||||
justify-content: center;
|
|
||||||
align-items: center;
|
|
||||||
text-align: center;
|
|
||||||
padding: 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.small > input::placeholder {
|
input::placeholder {
|
||||||
text-align: center;
|
text-align: center;
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
|
@ -81,12 +81,10 @@
|
||||||
|
|
||||||
.hierarchy-title {
|
.hierarchy-title {
|
||||||
align-items: center;
|
align-items: center;
|
||||||
text-transform: uppercase;
|
font-size: 18px;
|
||||||
font-size: 13px;
|
font-weight: 700;
|
||||||
font-weight: bold;
|
|
||||||
opacity: 0.6;
|
|
||||||
letter-spacing: 1px;
|
|
||||||
text-rendering: optimizeLegibility;
|
text-rendering: optimizeLegibility;
|
||||||
|
color: var(--ink);
|
||||||
}
|
}
|
||||||
|
|
||||||
.hierarchy {
|
.hierarchy {
|
||||||
|
|
|
@ -125,12 +125,10 @@
|
||||||
|
|
||||||
.hierarchy-title {
|
.hierarchy-title {
|
||||||
align-items: center;
|
align-items: center;
|
||||||
text-transform: uppercase;
|
font-size: 18px;
|
||||||
font-size: 13px;
|
font-weight: 700;
|
||||||
font-weight: bold;
|
|
||||||
opacity: 0.6;
|
|
||||||
letter-spacing: 1px;
|
|
||||||
text-rendering: optimizeLegibility;
|
text-rendering: optimizeLegibility;
|
||||||
|
color: var(--ink);
|
||||||
}
|
}
|
||||||
|
|
||||||
.hierarchy {
|
.hierarchy {
|
||||||
|
|
|
@ -1,19 +1,32 @@
|
||||||
<script>
|
<script>
|
||||||
import Button from "components/common/Button.svelte"
|
import Button from "components/common/Button.svelte"
|
||||||
export let apps
|
export let apps
|
||||||
|
|
||||||
|
function myFunction() {
|
||||||
|
var x = new Date(document.lastModified)
|
||||||
|
document.getElementById("demo").innerHTML = x
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="root">
|
<div class="root">
|
||||||
<div class="inner">
|
<div class="inner">
|
||||||
<img
|
|
||||||
src="/_builder/assets/budibase-logo.png"
|
|
||||||
class="logo"
|
|
||||||
alt="budibase logo" />
|
|
||||||
<div>
|
<div>
|
||||||
<div>
|
<div>
|
||||||
<h4 style="margin-bottom: 20px">Choose an Application</h4>
|
<div class="app-section-title">Your Web Apps</div>
|
||||||
{#each apps as app}
|
{#each apps as app}
|
||||||
<a href={`/_builder/${app._id}`} class="app-link">{app.name}</a>
|
<div class="apps-card">
|
||||||
|
<h3 class="app-title">{app.name}</h3>
|
||||||
|
<p class="app-desc">
|
||||||
|
A minimalist CRM which removes the noise and allows you to focus
|
||||||
|
on your business.
|
||||||
|
</p>
|
||||||
|
<div class="card-footer">
|
||||||
|
<div class="modified-date">Last Edited - 25th May 2020</div>
|
||||||
|
<a href={`/_builder/${app._id}`} class="app-button">
|
||||||
|
Open Web App
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
{/each}
|
{/each}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
@ -22,31 +35,68 @@
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
.root {
|
.root {
|
||||||
position: fixed;
|
margin: 40px 80px;
|
||||||
margin: 0 auto;
|
|
||||||
text-align: center;
|
|
||||||
top: 20%;
|
|
||||||
/*color: #333333;
|
|
||||||
background-color: #fdfdfd;*/
|
|
||||||
width: 100%;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.inner {
|
.app-section-title {
|
||||||
display: inline-block;
|
font-size: 20px;
|
||||||
margin: auto;
|
color: var(--ink);
|
||||||
|
font-weight: 700;
|
||||||
|
margin-bottom: 20px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.logo {
|
.apps {
|
||||||
width: 300px;
|
display: flex;
|
||||||
margin-bottom: 40px;
|
flex-wrap: wrap;
|
||||||
|
gap: 40px;
|
||||||
|
}
|
||||||
|
.apps-card {
|
||||||
|
background-color: var(--white);
|
||||||
|
padding: 20px;
|
||||||
|
max-width: 400px;
|
||||||
|
max-height: 150px;
|
||||||
|
border-radius: 5px;
|
||||||
|
border: 1px solid var(--grey-dark);
|
||||||
}
|
}
|
||||||
|
|
||||||
.root :global(.option) {
|
.app-button:hover {
|
||||||
width: 250px;
|
background-color: var(--grey-light);
|
||||||
|
text-decoration: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
.app-link {
|
.app-title {
|
||||||
margin-top: 10px;
|
font-size: 18px;
|
||||||
display: block;
|
font-weight: 700;
|
||||||
|
color: var(--ink);
|
||||||
|
text-transform: capitalize;
|
||||||
|
}
|
||||||
|
|
||||||
|
.app-desc {
|
||||||
|
color: var(--ink-light);
|
||||||
|
}
|
||||||
|
|
||||||
|
.card-footer {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: row;
|
||||||
|
align-items: baseline;
|
||||||
|
justify-content: space-between;
|
||||||
|
}
|
||||||
|
|
||||||
|
.modified-date {
|
||||||
|
font-size: 14px;
|
||||||
|
color: var(--ink-light);
|
||||||
|
}
|
||||||
|
|
||||||
|
.app-button {
|
||||||
|
background-color: var(--white);
|
||||||
|
color: var(--ink);
|
||||||
|
padding: 12px 20px;
|
||||||
|
border-radius: 5px;
|
||||||
|
border: 1px var(--grey) solid;
|
||||||
|
font-size: 14px;
|
||||||
|
font-weight: 400;
|
||||||
|
cursor: pointer;
|
||||||
|
transition: all 0.2s;
|
||||||
|
box-sizing: border-box;
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
|
@ -16,6 +16,11 @@
|
||||||
return props
|
return props
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const getComponentTypeName = component => {
|
||||||
|
let [componentName] = component._component.match(/[a-z]*$/)
|
||||||
|
return componentName || "element"
|
||||||
|
}
|
||||||
|
|
||||||
$: iframe &&
|
$: iframe &&
|
||||||
console.log(
|
console.log(
|
||||||
iframe.contentDocument.head.insertAdjacentHTML(
|
iframe.contentDocument.head.insertAdjacentHTML(
|
||||||
|
@ -60,7 +65,7 @@
|
||||||
_children: [
|
_children: [
|
||||||
{
|
{
|
||||||
_component: "@budibase/standard-components/container",
|
_component: "@budibase/standard-components/container",
|
||||||
_styles: { position: {}, layout: {} },
|
_styles: { normal: {}, hover: {}, active: {}, selected: {} },
|
||||||
_id: "__screenslot__text",
|
_id: "__screenslot__text",
|
||||||
_code: "",
|
_code: "",
|
||||||
className: "",
|
className: "",
|
||||||
|
@ -69,7 +74,12 @@
|
||||||
_children: [
|
_children: [
|
||||||
{
|
{
|
||||||
_component: "@budibase/standard-components/text",
|
_component: "@budibase/standard-components/text",
|
||||||
_styles: { position: {}, layout: {} },
|
_styles: {
|
||||||
|
normal: {},
|
||||||
|
hover: {},
|
||||||
|
active: {},
|
||||||
|
selected: {},
|
||||||
|
},
|
||||||
_id: "__screenslot__text_2",
|
_id: "__screenslot__text_2",
|
||||||
_code: "",
|
_code: "",
|
||||||
text: "content",
|
text: "content",
|
||||||
|
@ -88,6 +98,8 @@
|
||||||
appRootPath: "",
|
appRootPath: "",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$: selectedComponentType = getComponentTypeName($store.currentComponentInfo)
|
||||||
|
|
||||||
$: selectedComponentId = $store.currentComponentInfo
|
$: selectedComponentId = $store.currentComponentInfo
|
||||||
? $store.currentComponentInfo._id
|
? $store.currentComponentInfo._id
|
||||||
: ""
|
: ""
|
||||||
|
@ -102,6 +114,7 @@
|
||||||
srcdoc={iframeTemplate({
|
srcdoc={iframeTemplate({
|
||||||
styles,
|
styles,
|
||||||
stylesheetLinks,
|
stylesheetLinks,
|
||||||
|
selectedComponentType,
|
||||||
selectedComponentId,
|
selectedComponentId,
|
||||||
frontendDefinition: JSON.stringify(frontendDefinition),
|
frontendDefinition: JSON.stringify(frontendDefinition),
|
||||||
currentPageFunctions: $store.currentPageFunctions,
|
currentPageFunctions: $store.currentPageFunctions,
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
export default ({
|
export default ({
|
||||||
styles,
|
styles,
|
||||||
stylesheetLinks,
|
stylesheetLinks,
|
||||||
|
selectedComponentType,
|
||||||
selectedComponentId,
|
selectedComponentId,
|
||||||
frontendDefinition,
|
frontendDefinition,
|
||||||
currentPageFunctions,
|
currentPageFunctions,
|
||||||
|
@ -11,7 +12,7 @@ export default ({
|
||||||
<style>
|
<style>
|
||||||
${styles || ""}
|
${styles || ""}
|
||||||
|
|
||||||
.pos-${selectedComponentId} {
|
.${selectedComponentType}-${selectedComponentId} {
|
||||||
border: 2px solid #0055ff;
|
border: 2px solid #0055ff;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,35 @@
|
||||||
|
<script>
|
||||||
|
export let categories = []
|
||||||
|
export let selectedCategory = {}
|
||||||
|
export let onClick = category => {}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="tabs">
|
||||||
|
{#each categories as category}
|
||||||
|
<li
|
||||||
|
on:click={() => onClick(category)}
|
||||||
|
class:active={selectedCategory === category}>
|
||||||
|
{category.name}
|
||||||
|
</li>
|
||||||
|
{/each}
|
||||||
|
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.tabs {
|
||||||
|
display: flex;
|
||||||
|
list-style: none;
|
||||||
|
font-size: 18px;
|
||||||
|
font-weight: 700;
|
||||||
|
}
|
||||||
|
|
||||||
|
li {
|
||||||
|
color: var(--ink-lighter);
|
||||||
|
cursor: pointer;
|
||||||
|
margin-right: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.active {
|
||||||
|
color: var(--ink);
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -1,4 +1,5 @@
|
||||||
<script>
|
<script>
|
||||||
|
import { setContext, onMount } from "svelte"
|
||||||
import PropsView from "./PropsView.svelte"
|
import PropsView from "./PropsView.svelte"
|
||||||
import { store } from "builderStore"
|
import { store } from "builderStore"
|
||||||
import IconButton from "components/common/IconButton.svelte"
|
import IconButton from "components/common/IconButton.svelte"
|
||||||
|
@ -13,23 +14,63 @@
|
||||||
import LayoutEditor from "./LayoutEditor.svelte"
|
import LayoutEditor from "./LayoutEditor.svelte"
|
||||||
import EventsEditor from "./EventsEditor"
|
import EventsEditor from "./EventsEditor"
|
||||||
|
|
||||||
let current_view = "props"
|
import panelStructure from "./temporaryPanelStructure.js"
|
||||||
let codeEditor
|
import CategoryTab from "./CategoryTab.svelte"
|
||||||
|
import DesignView from "./DesignView.svelte"
|
||||||
|
import SettingsView from "./SettingsView.svelte"
|
||||||
|
|
||||||
|
let current_view = "design"
|
||||||
|
let codeEditor
|
||||||
|
let flattenedPanel = flattenComponents(panelStructure.categories)
|
||||||
|
let categories = [
|
||||||
|
{ value: "design", name: "Design" },
|
||||||
|
{ value: "settings", name: "Settings" },
|
||||||
|
{ value: "events", name: "Events" }
|
||||||
|
]
|
||||||
|
let selectedCategory = categories[0]
|
||||||
|
|
||||||
$: component = $store.currentComponentInfo
|
|
||||||
$: originalName = component.name
|
|
||||||
$: name =
|
|
||||||
$store.currentView === "detail"
|
|
||||||
? $store.currentPreviewItem.name
|
|
||||||
: component._component
|
|
||||||
$: description = component.description
|
|
||||||
$: components = $store.components
|
$: components = $store.components
|
||||||
|
$: componentInstance = $store.currentComponentInfo
|
||||||
|
$: componentDefinition = $store.components[componentInstance._component]
|
||||||
|
$: componentPropDefinition =
|
||||||
|
flattenedPanel.find(
|
||||||
|
//use for getting controls for each component property
|
||||||
|
c => c._component === componentInstance._component
|
||||||
|
) || {}
|
||||||
|
|
||||||
|
$: panelDefinition = componentPropDefinition.properties
|
||||||
|
? componentPropDefinition.properties[selectedCategory.value]
|
||||||
|
: {}
|
||||||
|
|
||||||
|
// SCREEN PROPS =============================================
|
||||||
$: screen_props =
|
$: screen_props =
|
||||||
$store.currentFrontEndType === "page"
|
$store.currentFrontEndType === "page"
|
||||||
? getProps($store.currentPreviewItem, ["name", "favicon"])
|
? getProps($store.currentPreviewItem, ["name", "favicon"])
|
||||||
: getProps($store.currentPreviewItem, ["name", "description", "route"])
|
: getProps($store.currentPreviewItem, ["name", "description", "route"])
|
||||||
|
|
||||||
const onStyleChanged = store.setComponentStyle
|
const onStyleChanged = store.setComponentStyle
|
||||||
|
const onPropChanged = store.setComponentProp
|
||||||
|
|
||||||
|
function walkProps(component, action) {
|
||||||
|
action(component)
|
||||||
|
if (component.children) {
|
||||||
|
for (let child of component.children) {
|
||||||
|
walkProps(child, action)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function flattenComponents(props) {
|
||||||
|
const components = []
|
||||||
|
props.forEach(comp =>
|
||||||
|
walkProps(comp, c => {
|
||||||
|
if ("_component" in c) {
|
||||||
|
components.push(c)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
)
|
||||||
|
return components
|
||||||
|
}
|
||||||
|
|
||||||
function getProps(obj, keys) {
|
function getProps(obj, keys) {
|
||||||
return keys.map((key, i) => [key, obj[key], obj.props._id + i])
|
return keys.map((key, i) => [key, obj[key], obj.props._id + i])
|
||||||
|
@ -37,116 +78,35 @@
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="root">
|
<div class="root">
|
||||||
<ul>
|
|
||||||
<li>
|
<CategoryTab
|
||||||
<button
|
onClick={category => (selectedCategory = category)}
|
||||||
class:selected={current_view === 'props'}
|
{categories}
|
||||||
on:click={() => (current_view = 'props')}>
|
{selectedCategory} />
|
||||||
<PaintIcon />
|
|
||||||
</button>
|
|
||||||
</li>
|
|
||||||
<li>
|
|
||||||
<button
|
|
||||||
class:selected={current_view === 'layout'}
|
|
||||||
on:click={() => (current_view = 'layout')}>
|
|
||||||
<LayoutIcon />
|
|
||||||
</button>
|
|
||||||
</li>
|
|
||||||
{#if !component._component.startsWith('##')}
|
|
||||||
<li>
|
|
||||||
<button
|
|
||||||
class:selected={current_view === 'code'}
|
|
||||||
on:click={() => codeEditor && codeEditor.show()}>
|
|
||||||
{#if component._code && component._code.trim().length > 0}
|
|
||||||
<div class="button-indicator">
|
|
||||||
<CircleIndicator />
|
|
||||||
</div>
|
|
||||||
{/if}
|
|
||||||
<TerminalIcon />
|
|
||||||
</button>
|
|
||||||
</li>
|
|
||||||
<li>
|
|
||||||
<button
|
|
||||||
class:selected={current_view === 'events'}
|
|
||||||
on:click={() => (current_view = 'events')}>
|
|
||||||
<EventsIcon />
|
|
||||||
</button>
|
|
||||||
</li>
|
|
||||||
{/if}
|
|
||||||
</ul>
|
|
||||||
<div class="component-props-container">
|
<div class="component-props-container">
|
||||||
|
{#if selectedCategory.value === 'design'}
|
||||||
{#if current_view === 'props'}
|
<DesignView {panelDefinition} {componentInstance} {onStyleChanged} />
|
||||||
{#if $store.currentView === 'detail'}
|
{:else if selectedCategory.value === 'settings'}
|
||||||
{#each screen_props as [k, v, id] (id)}
|
<SettingsView
|
||||||
<div class="detail-prop" for={k}>
|
{componentInstance}
|
||||||
<label>{k}:</label>
|
{componentDefinition}
|
||||||
<input
|
{panelDefinition}
|
||||||
id={k}
|
onChange={onPropChanged} />
|
||||||
value={v}
|
{:else if selectedCategory.value === 'events'}
|
||||||
on:input={({ target }) => store.setMetadataProp(k, target.value)} />
|
<EventsEditor component={componentInstance} />
|
||||||
</div>
|
|
||||||
{/each}
|
|
||||||
<PropsView {component} {components} />
|
|
||||||
{:else}
|
|
||||||
<PropsView {component} {components} />
|
|
||||||
{/if}
|
{/if}
|
||||||
{:else if current_view === 'layout'}
|
|
||||||
<LayoutEditor {onStyleChanged} {component} />
|
|
||||||
{:else if current_view === 'events'}
|
|
||||||
<EventsEditor {component} {components} />
|
|
||||||
{/if}
|
|
||||||
|
|
||||||
<CodeEditor
|
|
||||||
bind:this={codeEditor}
|
|
||||||
code={component._code}
|
|
||||||
onCodeChanged={store.setComponentCode} />
|
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
.detail-prop {
|
|
||||||
height: 40px;
|
|
||||||
margin-bottom: 15px;
|
|
||||||
display: grid;
|
|
||||||
grid-template-rows: 1fr;
|
|
||||||
grid-template-columns: 70px 1fr;
|
|
||||||
grid-gap: 10px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.detail-prop label {
|
|
||||||
word-wrap: break-word;
|
|
||||||
font-size: 13px;
|
|
||||||
font-weight: 700;
|
|
||||||
color: #163057;
|
|
||||||
opacity: 0.6;
|
|
||||||
padding-top: 13px;
|
|
||||||
margin-bottom: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
input {
|
|
||||||
height: 30px;
|
|
||||||
padding-left: 8px;
|
|
||||||
padding-right: 8px;
|
|
||||||
border: 1px solid #dbdbdb;
|
|
||||||
border-radius: 2px;
|
|
||||||
opacity: 0.5;
|
|
||||||
}
|
|
||||||
|
|
||||||
input:focus {
|
|
||||||
outline: 0;
|
|
||||||
background-color: #fff;
|
|
||||||
color: #666;
|
|
||||||
border-color: #1e87f0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.root {
|
.root {
|
||||||
height: 100%;
|
height: 100%;
|
||||||
padding: 20px;
|
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
|
overflow-x: hidden;
|
||||||
}
|
}
|
||||||
|
|
||||||
.title > div:nth-child(1) {
|
.title > div:nth-child(1) {
|
||||||
|
@ -159,55 +119,7 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
.component-props-container {
|
.component-props-container {
|
||||||
margin-top: 10px;
|
margin-top: 20px;
|
||||||
flex: 1 1 auto;
|
flex: 1 1 auto;
|
||||||
}
|
}
|
||||||
|
|
||||||
ul {
|
|
||||||
list-style: none;
|
|
||||||
display: flex;
|
|
||||||
justify-content: space-between;
|
|
||||||
padding: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
li {
|
|
||||||
background: none;
|
|
||||||
border-radius: 3px;
|
|
||||||
width: 48px;
|
|
||||||
height: 48px;
|
|
||||||
}
|
|
||||||
|
|
||||||
li button {
|
|
||||||
width: 48px;
|
|
||||||
height: 48px;
|
|
||||||
background: none;
|
|
||||||
border: none;
|
|
||||||
border-radius: 3px;
|
|
||||||
padding: 7px;
|
|
||||||
outline: none;
|
|
||||||
cursor: pointer;
|
|
||||||
position: relative;
|
|
||||||
}
|
|
||||||
|
|
||||||
li:nth-last-child(1) {
|
|
||||||
margin-right: 0px;
|
|
||||||
background: none;
|
|
||||||
border-radius: 3px;
|
|
||||||
width: 48px;
|
|
||||||
height: 48px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.selected {
|
|
||||||
color: var(--button-text);
|
|
||||||
background: #f9f9f9 !important;
|
|
||||||
width: 48px;
|
|
||||||
height: 48px;
|
|
||||||
}
|
|
||||||
|
|
||||||
.button-indicator {
|
|
||||||
position: absolute;
|
|
||||||
top: 8px;
|
|
||||||
right: 10px;
|
|
||||||
color: var(--button-text);
|
|
||||||
}
|
|
||||||
</style>
|
</style>
|
||||||
|
|
|
@ -2,6 +2,7 @@
|
||||||
import { splitName } from "./pagesParsing/splitRootComponentName.js"
|
import { splitName } from "./pagesParsing/splitRootComponentName.js"
|
||||||
import components from "./temporaryPanelStructure.js"
|
import components from "./temporaryPanelStructure.js"
|
||||||
import ConfirmDialog from "components/common/ConfirmDialog.svelte"
|
import ConfirmDialog from "components/common/ConfirmDialog.svelte"
|
||||||
|
import CategoryTab from "./CategoryTab.svelte"
|
||||||
import {
|
import {
|
||||||
find,
|
find,
|
||||||
sortBy,
|
sortBy,
|
||||||
|
@ -36,15 +37,12 @@
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="root">
|
<div class="root">
|
||||||
<ul class="tabs">
|
|
||||||
{#each categories as category}
|
<CategoryTab
|
||||||
<li
|
onClick={category => (selectedCategory = category)}
|
||||||
on:click={() => (selectedCategory = category)}
|
{selectedCategory}
|
||||||
class:active={selectedCategory === category}>
|
{categories} />
|
||||||
{category.name}
|
|
||||||
</li>
|
|
||||||
{/each}
|
|
||||||
</ul>
|
|
||||||
<div class="panel">
|
<div class="panel">
|
||||||
<Tab
|
<Tab
|
||||||
list={selectedCategory}
|
list={selectedCategory}
|
||||||
|
|
|
@ -24,13 +24,13 @@
|
||||||
<button
|
<button
|
||||||
class:selected={selected === COMPONENT_SELECTION_TAB}
|
class:selected={selected === COMPONENT_SELECTION_TAB}
|
||||||
on:click={() => selectTab(COMPONENT_SELECTION_TAB)}>
|
on:click={() => selectTab(COMPONENT_SELECTION_TAB)}>
|
||||||
Components
|
Add
|
||||||
</button>
|
</button>
|
||||||
|
|
||||||
<button
|
<button
|
||||||
class:selected={selected === PROPERTIES_TAB}
|
class:selected={selected === PROPERTIES_TAB}
|
||||||
on:click={() => selectTab(PROPERTIES_TAB)}>
|
on:click={() => selectTab(PROPERTIES_TAB)}>
|
||||||
Properties
|
Edit
|
||||||
</button>
|
</button>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
|
@ -54,33 +54,28 @@
|
||||||
height: 100%;
|
height: 100%;
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: column;
|
flex-direction: column;
|
||||||
padding: 20px 0;
|
padding: 20px 20px;
|
||||||
|
border-left: solid 1px #e8e8ef;
|
||||||
}
|
}
|
||||||
|
|
||||||
.switcher {
|
.switcher {
|
||||||
display: flex;
|
display: flex;
|
||||||
justify-content: space-between;
|
margin: 0px 20px 20px 0px;
|
||||||
margin: 20px;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.switcher > button {
|
.switcher > button {
|
||||||
text-rendering: optimizeLegibility;
|
|
||||||
display: inline-block;
|
display: inline-block;
|
||||||
border: none;
|
border: none;
|
||||||
margin: 0;
|
margin: 0;
|
||||||
padding: 0;
|
padding: 0;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
font-size: 14px;
|
font-size: 18px;
|
||||||
text-transform: uppercase;
|
font-weight: 700;
|
||||||
background: rgba(0, 0, 0, 0);
|
color: var(--ink-lighter);
|
||||||
font-weight: 500;
|
|
||||||
color: var(--secondary40);
|
|
||||||
margin-right: 20px;
|
margin-right: 20px;
|
||||||
letter-spacing: 1px;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.switcher > .selected {
|
.switcher > .selected {
|
||||||
color: var(--secondary100);
|
color: var(--ink);
|
||||||
font-weight: 600;
|
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
|
@ -0,0 +1,71 @@
|
||||||
|
<script>
|
||||||
|
import PropertyGroup from "./PropertyGroup.svelte"
|
||||||
|
import FlatButtonGroup from "./FlatButtonGroup.svelte"
|
||||||
|
|
||||||
|
export let panelDefinition = {}
|
||||||
|
export let componentInstance = {}
|
||||||
|
export let componentDefinition = {}
|
||||||
|
export let onStyleChanged = () => {}
|
||||||
|
|
||||||
|
let selectedCategory = "normal"
|
||||||
|
|
||||||
|
const getProperties = name => panelDefinition[name]
|
||||||
|
|
||||||
|
function onChange(category) {
|
||||||
|
selectedCategory = category
|
||||||
|
}
|
||||||
|
|
||||||
|
const buttonProps = [
|
||||||
|
{ value: "normal", text: "Normal" },
|
||||||
|
{ value: "hover", text: "Hover" },
|
||||||
|
{ value: "active", text: "Active" },
|
||||||
|
{ value: "selected", text: "Selected" },
|
||||||
|
]
|
||||||
|
|
||||||
|
$: propertyGroupNames = Object.keys(panelDefinition)
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="design-view-container">
|
||||||
|
|
||||||
|
<div class="design-view-state-categories">
|
||||||
|
<FlatButtonGroup value={selectedCategory} {buttonProps} {onChange} />
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="design-view-property-groups">
|
||||||
|
{#if propertyGroupNames.length > 0}
|
||||||
|
{#each propertyGroupNames as groupName}
|
||||||
|
<PropertyGroup
|
||||||
|
name={groupName}
|
||||||
|
properties={getProperties(groupName)}
|
||||||
|
styleCategory={selectedCategory}
|
||||||
|
{onStyleChanged}
|
||||||
|
{componentDefinition}
|
||||||
|
{componentInstance} />
|
||||||
|
{/each}
|
||||||
|
{:else}
|
||||||
|
<div class="no-design">
|
||||||
|
<span>This component does not have any design properties</span>
|
||||||
|
</div>
|
||||||
|
{/if}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.design-view-container {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
width: 100%;
|
||||||
|
}
|
||||||
|
|
||||||
|
.design-view-state-categories {
|
||||||
|
flex: 0 0 50px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.design-view-property-groups {
|
||||||
|
flex: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
.no-design {
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -25,16 +25,14 @@
|
||||||
export const EVENT_TYPE = "event"
|
export const EVENT_TYPE = "event"
|
||||||
|
|
||||||
export let component
|
export let component
|
||||||
export let components
|
|
||||||
|
|
||||||
let modalOpen = false
|
let modalOpen = false
|
||||||
let events = []
|
let events = []
|
||||||
let selectedEvent = null
|
let selectedEvent = null
|
||||||
|
|
||||||
$: {
|
$: {
|
||||||
const componentDefinition = components[component._component]
|
events = Object.keys(component)
|
||||||
events = Object.keys(componentDefinition.props)
|
.filter(propName => ["onChange", "onClick", "onLoad"].includes(propName))
|
||||||
.filter(propName => componentDefinition.props[propName] === EVENT_TYPE)
|
|
||||||
.map(propName => ({
|
.map(propName => ({
|
||||||
name: propName,
|
name: propName,
|
||||||
handlers: component[propName] || [],
|
handlers: component[propName] || [],
|
||||||
|
|
|
@ -0,0 +1,38 @@
|
||||||
|
<script>
|
||||||
|
export let value = ""
|
||||||
|
export let text = ""
|
||||||
|
export let icon = ""
|
||||||
|
export let onClick = value => {}
|
||||||
|
export let selected = false
|
||||||
|
|
||||||
|
$: useIcon = !!icon
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="flatbutton" class:selected on:click={() => onClick(value || text)}>
|
||||||
|
{#if useIcon}
|
||||||
|
<i class={icon} />
|
||||||
|
{:else}
|
||||||
|
<span>{text}</span>
|
||||||
|
{/if}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.flatbutton {
|
||||||
|
cursor: pointer;
|
||||||
|
padding: 8px 4px;
|
||||||
|
text-align: center;
|
||||||
|
background: #ffffff;
|
||||||
|
color: var(--ink-light);
|
||||||
|
border-radius: 5px;
|
||||||
|
font-family: Roboto;
|
||||||
|
font-size: 13px;
|
||||||
|
font-weight: 500;
|
||||||
|
transition: background 0.5s, color 0.5s ease;
|
||||||
|
text-rendering: optimizeLegibility;
|
||||||
|
}
|
||||||
|
|
||||||
|
.selected {
|
||||||
|
background: #808192;
|
||||||
|
color: #ffffff;
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -0,0 +1,52 @@
|
||||||
|
<script>
|
||||||
|
import { onMount } from "svelte"
|
||||||
|
|
||||||
|
import FlatButton from "./FlatButton.svelte"
|
||||||
|
export let buttonProps = []
|
||||||
|
export let isMultiSelect = false
|
||||||
|
export let value = []
|
||||||
|
export let initialValue = ""
|
||||||
|
export let onChange = selected => {}
|
||||||
|
|
||||||
|
onMount(() => {
|
||||||
|
if (!value && !!initialValue) {
|
||||||
|
value = initialValue
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
function onButtonClicked(v) {
|
||||||
|
let val
|
||||||
|
if (isMultiSelect) {
|
||||||
|
if (value.includes(v)) {
|
||||||
|
let idx = value.findIndex(i => i === v)
|
||||||
|
val = [...value].splice(idx, 1)
|
||||||
|
} else {
|
||||||
|
val = [...value, v]
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
val = v
|
||||||
|
}
|
||||||
|
onChange(val)
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="flatbutton-group">
|
||||||
|
{#each buttonProps as props}
|
||||||
|
<div class="button-container">
|
||||||
|
<FlatButton
|
||||||
|
selected={value.includes(props.value)}
|
||||||
|
onClick={onButtonClicked}
|
||||||
|
{...props} />
|
||||||
|
</div>
|
||||||
|
{/each}
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.flatbutton-group {
|
||||||
|
display: flex;
|
||||||
|
}
|
||||||
|
|
||||||
|
.button-container {
|
||||||
|
flex: 1;
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -0,0 +1,36 @@
|
||||||
|
<script>
|
||||||
|
import { onMount } from "svelte"
|
||||||
|
export let value = ""
|
||||||
|
export let onChange = value => {}
|
||||||
|
export let options = []
|
||||||
|
export let initialValue = ""
|
||||||
|
export let styleBindingProperty = ""
|
||||||
|
|
||||||
|
const handleStyleBind = value =>
|
||||||
|
!!styleBindingProperty ? { style: `${styleBindingProperty}: ${value}` } : {}
|
||||||
|
|
||||||
|
$: isOptionsObject = options.every(o => typeof o === "object")
|
||||||
|
|
||||||
|
onMount(() => {
|
||||||
|
if (!value && !!initialValue) {
|
||||||
|
value = initialValue
|
||||||
|
}
|
||||||
|
})
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<select
|
||||||
|
class="uk-select uk-form-small"
|
||||||
|
{value}
|
||||||
|
on:change={ev => onChange(ev.target.value)}>
|
||||||
|
{#if isOptionsObject}
|
||||||
|
{#each options as { value, label }}
|
||||||
|
<option {...handleStyleBind(value || label)} value={value || label}>
|
||||||
|
{label}
|
||||||
|
</option>
|
||||||
|
{/each}
|
||||||
|
{:else}
|
||||||
|
{#each options as value}
|
||||||
|
<option {...handleStyleBind(value)} {value}>{value}</option>
|
||||||
|
{/each}
|
||||||
|
{/if}
|
||||||
|
</select>
|
|
@ -0,0 +1,66 @@
|
||||||
|
<script>
|
||||||
|
import { onMount, getContext } from "svelte"
|
||||||
|
|
||||||
|
export let label = ""
|
||||||
|
export let control = null
|
||||||
|
export let key = ""
|
||||||
|
export let value
|
||||||
|
export let props = {}
|
||||||
|
export let onChange = () => {}
|
||||||
|
|
||||||
|
function handleChange(key, v) {
|
||||||
|
if (v.target) {
|
||||||
|
let val = props.valueKey ? v.target[props.valueKey] : v.target.value
|
||||||
|
onChange(key, val)
|
||||||
|
} else {
|
||||||
|
onChange(key, v)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const safeValue = () => {
|
||||||
|
return value === undefined && props.defaultValue !== undefined
|
||||||
|
? props.defaultValue
|
||||||
|
: value
|
||||||
|
}
|
||||||
|
|
||||||
|
//Incase the component has a different value key name
|
||||||
|
const handlevalueKey = value =>
|
||||||
|
props.valueKey ? { [props.valueKey]: safeValue() } : { value: safeValue() }
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="property-control">
|
||||||
|
<div class="label">{label}</div>
|
||||||
|
<div class="control">
|
||||||
|
<svelte:component
|
||||||
|
this={control}
|
||||||
|
{...handlevalueKey(value)}
|
||||||
|
on:change={val => handleChange(key, val)}
|
||||||
|
onChange={val => handleChange(key, val)}
|
||||||
|
{...props} />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.property-control {
|
||||||
|
display: flex;
|
||||||
|
flex-flow: row;
|
||||||
|
margin: 8px 0px;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.label {
|
||||||
|
flex: 0 0 50px;
|
||||||
|
font-size: 12px;
|
||||||
|
font-weight: 400;
|
||||||
|
text-align: left;
|
||||||
|
color: var(--ink);
|
||||||
|
margin-right: auto;
|
||||||
|
text-transform: capitalize;
|
||||||
|
}
|
||||||
|
|
||||||
|
.control {
|
||||||
|
flex: 1;
|
||||||
|
padding-left: 2px;
|
||||||
|
max-width: 164px;
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -0,0 +1,82 @@
|
||||||
|
<script>
|
||||||
|
import { excludeProps } from "./propertyCategories.js"
|
||||||
|
import PropertyControl from "./PropertyControl.svelte"
|
||||||
|
|
||||||
|
export let name = ""
|
||||||
|
export let styleCategory = "normal"
|
||||||
|
export let properties = []
|
||||||
|
export let componentInstance = {}
|
||||||
|
export let onStyleChanged = () => {}
|
||||||
|
|
||||||
|
export let show = false
|
||||||
|
|
||||||
|
const capitalize = name => name[0].toUpperCase() + name.slice(1)
|
||||||
|
|
||||||
|
$: icon = show ? "ri-arrow-down-s-fill" : "ri-arrow-right-s-fill"
|
||||||
|
$: style = componentInstance["_styles"][styleCategory] || {}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="property-group-container">
|
||||||
|
<div class="property-group-name" on:click={() => (show = !show)}>
|
||||||
|
<div class="icon">
|
||||||
|
<i class={icon} />
|
||||||
|
</div>
|
||||||
|
<div class="name">{capitalize(name)}</div>
|
||||||
|
</div>
|
||||||
|
<div class="property-panel" class:show>
|
||||||
|
|
||||||
|
{#each properties as props}
|
||||||
|
<PropertyControl
|
||||||
|
label={props.label}
|
||||||
|
control={props.control}
|
||||||
|
key={props.key}
|
||||||
|
value={style[props.key]}
|
||||||
|
onChange={(key, value) => onStyleChanged(styleCategory, key, value)}
|
||||||
|
props={{ ...excludeProps(props, ['control', 'label']) }} />
|
||||||
|
{/each}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.property-group-container {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
height: auto;
|
||||||
|
background: var(--grey-light);
|
||||||
|
margin: 0px 0px 4px 0px;
|
||||||
|
padding: 8px 12px;
|
||||||
|
justify-content: center;
|
||||||
|
border-radius: 4px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.property-group-name {
|
||||||
|
cursor: pointer;
|
||||||
|
display: flex;
|
||||||
|
flex-flow: row nowrap;
|
||||||
|
}
|
||||||
|
|
||||||
|
.name {
|
||||||
|
flex: 1;
|
||||||
|
text-align: left;
|
||||||
|
padding-top: 2px;
|
||||||
|
font-size: 14px;
|
||||||
|
font-weight: 500;
|
||||||
|
letter-spacing: 0.14px;
|
||||||
|
color: var(--ink);
|
||||||
|
}
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
flex: 0 0 20px;
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.property-panel {
|
||||||
|
height: 0px;
|
||||||
|
overflow: hidden;
|
||||||
|
}
|
||||||
|
|
||||||
|
.show {
|
||||||
|
overflow: auto;
|
||||||
|
height: auto;
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -0,0 +1,41 @@
|
||||||
|
<script>
|
||||||
|
import PropertyControl from "./PropertyControl.svelte"
|
||||||
|
import InputGroup from "../common/Inputs/InputGroup.svelte"
|
||||||
|
import Colorpicker from "../common/Colorpicker.svelte"
|
||||||
|
import { excludeProps } from "./propertyCategories.js"
|
||||||
|
|
||||||
|
export let panelDefinition = []
|
||||||
|
export let componentDefinition = {}
|
||||||
|
export let componentInstance = {}
|
||||||
|
export let onChange = () => {}
|
||||||
|
|
||||||
|
const propExistsOnComponentDef = prop => prop in componentDefinition.props
|
||||||
|
|
||||||
|
function handleChange(key, data) {
|
||||||
|
data.target ? onChange(key, data.target.value) : onChange(key, data)
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
{#if panelDefinition.length > 0}
|
||||||
|
{#each panelDefinition as definition}
|
||||||
|
{#if propExistsOnComponentDef(definition.key)}
|
||||||
|
<PropertyControl
|
||||||
|
control={definition.control}
|
||||||
|
label={definition.label}
|
||||||
|
key={definition.key}
|
||||||
|
value={componentInstance[definition.key]}
|
||||||
|
{onChange}
|
||||||
|
props={{ ...excludeProps(definition, ['control', 'label']) }} />
|
||||||
|
{/if}
|
||||||
|
{/each}
|
||||||
|
{:else}
|
||||||
|
<div>
|
||||||
|
<span>This component does not have any settings.</span>
|
||||||
|
</div>
|
||||||
|
{/if}
|
||||||
|
|
||||||
|
<style>
|
||||||
|
div {
|
||||||
|
text-align: center;
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -0,0 +1,240 @@
|
||||||
|
<script>
|
||||||
|
import ComponentsHierarchy from "./ComponentsHierarchy.svelte"
|
||||||
|
import ComponentsHierarchyChildren from "./ComponentsHierarchyChildren.svelte"
|
||||||
|
import PageLayout from "./PageLayout.svelte"
|
||||||
|
import PagesList from "./PagesList.svelte"
|
||||||
|
import { store } from "builderStore"
|
||||||
|
import IconButton from "components/common/IconButton.svelte"
|
||||||
|
import NewScreen from "./NewScreen.svelte"
|
||||||
|
import CurrentItemPreview from "./CurrentItemPreview.svelte"
|
||||||
|
import SettingsView from "./SettingsView.svelte"
|
||||||
|
import PageView from "./PageView.svelte"
|
||||||
|
import ComponentsPaneSwitcher from "./ComponentsPaneSwitcher.svelte"
|
||||||
|
import ConfirmDialog from "components/common/ConfirmDialog.svelte"
|
||||||
|
import { last } from "lodash/fp"
|
||||||
|
import { AddIcon } from "components/common/Icons"
|
||||||
|
|
||||||
|
let newScreenPicker
|
||||||
|
let confirmDeleteDialog
|
||||||
|
let componentToDelete = ""
|
||||||
|
|
||||||
|
const newScreen = () => {
|
||||||
|
newScreenPicker.show()
|
||||||
|
}
|
||||||
|
|
||||||
|
let settingsView
|
||||||
|
const settings = () => {
|
||||||
|
settingsView.show()
|
||||||
|
}
|
||||||
|
|
||||||
|
const confirmDeleteComponent = component => {
|
||||||
|
componentToDelete = component
|
||||||
|
confirmDeleteDialog.show()
|
||||||
|
}
|
||||||
|
|
||||||
|
const lastPartOfName = c => (c ? last(c.split("/")) : "")
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="root">
|
||||||
|
|
||||||
|
<div class="ui-nav">
|
||||||
|
|
||||||
|
<div class="pages-list-container">
|
||||||
|
<div class="nav-header">
|
||||||
|
<span class="navigator-title">Navigator</span>
|
||||||
|
<div class="border-line" />
|
||||||
|
|
||||||
|
<span class="components-nav-page">Pages</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="nav-items-container">
|
||||||
|
<PagesList />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="border-line" />
|
||||||
|
|
||||||
|
<PageLayout layout={$store.pages[$store.currentPageName]} />
|
||||||
|
|
||||||
|
<div class="border-line" />
|
||||||
|
|
||||||
|
<div class="components-list-container">
|
||||||
|
<div class="nav-group-header">
|
||||||
|
<span class="components-nav-header" style="margin-top: 0;">
|
||||||
|
Screens
|
||||||
|
</span>
|
||||||
|
<div>
|
||||||
|
<button on:click={newScreen}>
|
||||||
|
<AddIcon />
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="nav-items-container">
|
||||||
|
<ComponentsHierarchy screens={$store.screens} />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="preview-pane">
|
||||||
|
<CurrentItemPreview />
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{#if $store.currentFrontEndType === 'screen' || $store.currentFrontEndType === 'page'}
|
||||||
|
<div class="components-pane">
|
||||||
|
<ComponentsPaneSwitcher />
|
||||||
|
</div>
|
||||||
|
{/if}
|
||||||
|
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<NewScreen bind:this={newScreenPicker} />
|
||||||
|
<SettingsView bind:this={settingsView} />
|
||||||
|
|
||||||
|
<ConfirmDialog
|
||||||
|
bind:this={confirmDeleteDialog}
|
||||||
|
title="Confirm Delete"
|
||||||
|
body={`Are you sure you wish to delete this '${lastPartOfName(componentToDelete)}' component`}
|
||||||
|
okText="Delete Component"
|
||||||
|
onOk={() => store.deleteComponent(componentToDelete)} />
|
||||||
|
|
||||||
|
<style>
|
||||||
|
button {
|
||||||
|
cursor: pointer;
|
||||||
|
outline: none;
|
||||||
|
border: none;
|
||||||
|
border-radius: 5px;
|
||||||
|
width: 20px;
|
||||||
|
padding-bottom: 10px;
|
||||||
|
display: flex;
|
||||||
|
justify-content: center;
|
||||||
|
align-items: center;
|
||||||
|
padding: 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.root {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 275px 1fr 300px;
|
||||||
|
height: 100%;
|
||||||
|
width: 100%;
|
||||||
|
background: #fafafa;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media only screen and (min-width: 1800px) {
|
||||||
|
.root {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 300px 1fr 300px;
|
||||||
|
height: 100%;
|
||||||
|
width: 100%;
|
||||||
|
background: #fafafa;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.ui-nav {
|
||||||
|
grid-column: 1;
|
||||||
|
background-color: var(--white);
|
||||||
|
height: calc(100vh - 49px);
|
||||||
|
padding: 0;
|
||||||
|
overflow: scroll;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
}
|
||||||
|
|
||||||
|
.preview-pane {
|
||||||
|
grid-column: 2;
|
||||||
|
margin: 40px;
|
||||||
|
background: #fff;
|
||||||
|
border-radius: 5px;
|
||||||
|
box-shadow: 0 0px 6px rgba(0, 0, 0, 0.05);
|
||||||
|
}
|
||||||
|
|
||||||
|
.components-pane {
|
||||||
|
grid-column: 3;
|
||||||
|
background-color: var(--white);
|
||||||
|
height: 100vh;
|
||||||
|
overflow-y: scroll;
|
||||||
|
}
|
||||||
|
|
||||||
|
.components-nav-page {
|
||||||
|
font-size: 13px;
|
||||||
|
color: #000333;
|
||||||
|
text-transform: uppercase;
|
||||||
|
padding-left: 20px;
|
||||||
|
margin-top: 20px;
|
||||||
|
font-weight: 600;
|
||||||
|
opacity: 0.4;
|
||||||
|
letter-spacing: 1px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.components-nav-header {
|
||||||
|
font-size: 13px;
|
||||||
|
color: #000333;
|
||||||
|
text-transform: uppercase;
|
||||||
|
margin-top: 20px;
|
||||||
|
font-weight: 600;
|
||||||
|
opacity: 0.4;
|
||||||
|
letter-spacing: 1px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-header {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
margin-top: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-items-container {
|
||||||
|
padding: 1rem 0rem 0rem 0rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-group-header {
|
||||||
|
display: flex;
|
||||||
|
padding: 0px 20px 0px 20px;
|
||||||
|
font-size: 0.9rem;
|
||||||
|
font-weight: bold;
|
||||||
|
justify-content: space-between;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-group-header > div:nth-child(1) {
|
||||||
|
padding: 0rem 0.5rem 0rem 0rem;
|
||||||
|
vertical-align: bottom;
|
||||||
|
grid-column-start: icon;
|
||||||
|
margin-right: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-group-header > span:nth-child(3) {
|
||||||
|
margin-left: 5px;
|
||||||
|
vertical-align: bottom;
|
||||||
|
grid-column-start: title;
|
||||||
|
margin-top: auto;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-group-header > div:nth-child(3) {
|
||||||
|
vertical-align: bottom;
|
||||||
|
grid-column-start: button;
|
||||||
|
cursor: pointer;
|
||||||
|
color: var(--primary75);
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-group-header > div:nth-child(3):hover {
|
||||||
|
color: var(--primary75);
|
||||||
|
}
|
||||||
|
|
||||||
|
.navigator-title {
|
||||||
|
font-size: 14px;
|
||||||
|
color: var(--secondary100);
|
||||||
|
font-weight: 600;
|
||||||
|
text-transform: uppercase;
|
||||||
|
padding: 0 20px 20px 20px;
|
||||||
|
line-height: 1rem !important;
|
||||||
|
letter-spacing: 1px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.border-line {
|
||||||
|
border-bottom: 1px solid #d8d8d8;
|
||||||
|
}
|
||||||
|
|
||||||
|
.components-list-container {
|
||||||
|
padding: 20px 0px 0 0;
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -24,7 +24,7 @@ export const createProps = (componentDefinition, derivedFromProps) => {
|
||||||
const props = {
|
const props = {
|
||||||
_id: uuid(),
|
_id: uuid(),
|
||||||
_component: componentDefinition._component,
|
_component: componentDefinition._component,
|
||||||
_styles: { position: {}, layout: {} },
|
_styles: { normal: {}, hover: {}, active: {}, selected: {} },
|
||||||
_code: "",
|
_code: "",
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -71,7 +71,7 @@ export const makePropsSafe = (componentDefinition, props) => {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!props._styles) {
|
if (!props._styles) {
|
||||||
props._styles = { layout: {}, position: {} }
|
props._styles = { normal: {}, hover: {}, active: {}, selected: {} }
|
||||||
}
|
}
|
||||||
|
|
||||||
return props
|
return props
|
||||||
|
|
|
@ -0,0 +1,173 @@
|
||||||
|
import Input from "../common/Input.svelte"
|
||||||
|
import OptionSelect from "./OptionSelect.svelte"
|
||||||
|
import InputGroup from "../common/Inputs/InputGroup.svelte"
|
||||||
|
// import Colorpicker from "../common/Colorpicker.svelte"
|
||||||
|
/*
|
||||||
|
TODO: Allow for default values for all properties
|
||||||
|
*/
|
||||||
|
|
||||||
|
export const layout = [
|
||||||
|
{
|
||||||
|
label: "Direction",
|
||||||
|
key: "flex-direction",
|
||||||
|
control: OptionSelect,
|
||||||
|
initialValue: "columnReverse",
|
||||||
|
options: [
|
||||||
|
{ label: "row" },
|
||||||
|
{ label: "row-reverse", value: "rowReverse" },
|
||||||
|
{ label: "column" },
|
||||||
|
{ label: "column-reverse", value: "columnReverse" },
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{ label: "Justify", key: "justify-content", control: Input },
|
||||||
|
{ label: "Align", key: "align-items", control: Input },
|
||||||
|
{
|
||||||
|
label: "Wrap",
|
||||||
|
key: "flex-wrap",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: [{ label: "wrap" }, { label: "no wrap", value: "noWrap" }],
|
||||||
|
},
|
||||||
|
]
|
||||||
|
|
||||||
|
const spacingMeta = [
|
||||||
|
{ placeholder: "T" },
|
||||||
|
{ placeholder: "R" },
|
||||||
|
{ placeholder: "B" },
|
||||||
|
{ placeholder: "L" },
|
||||||
|
]
|
||||||
|
export const spacing = [
|
||||||
|
{
|
||||||
|
label: "Padding",
|
||||||
|
key: "padding",
|
||||||
|
control: InputGroup,
|
||||||
|
meta: spacingMeta,
|
||||||
|
},
|
||||||
|
{ label: "Margin", key: "margin", control: InputGroup, meta: spacingMeta },
|
||||||
|
]
|
||||||
|
|
||||||
|
export const size = [
|
||||||
|
{ label: "Width", key: "width", control: Input },
|
||||||
|
{ label: "Height", key: "height", control: Input },
|
||||||
|
{ label: "Min W", key: "min-width", control: Input },
|
||||||
|
{ label: "Min H", key: "min-height", control: Input },
|
||||||
|
{ label: "Max W", key: "max-width", control: Input },
|
||||||
|
{ label: "Max H", key: "max-height", control: Input },
|
||||||
|
]
|
||||||
|
|
||||||
|
export const position = [
|
||||||
|
{
|
||||||
|
label: "Position",
|
||||||
|
key: "position",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: [
|
||||||
|
{ label: "static" },
|
||||||
|
{ label: "relative" },
|
||||||
|
{ label: "fixed" },
|
||||||
|
{ label: "absolute" },
|
||||||
|
{ label: "sticky" },
|
||||||
|
],
|
||||||
|
},
|
||||||
|
]
|
||||||
|
|
||||||
|
export const typography = [
|
||||||
|
{
|
||||||
|
label: "Font",
|
||||||
|
key: "font-family",
|
||||||
|
control: OptionSelect,
|
||||||
|
defaultValue: "initial",
|
||||||
|
options: [
|
||||||
|
"initial",
|
||||||
|
"Times New Roman",
|
||||||
|
"Georgia",
|
||||||
|
"Arial",
|
||||||
|
"Arial Black",
|
||||||
|
"Comic Sans MS",
|
||||||
|
"Impact",
|
||||||
|
"Lucida Sans Unicode",
|
||||||
|
],
|
||||||
|
styleBindingProperty: "font-family",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "Weight",
|
||||||
|
key: "font-weight",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: [
|
||||||
|
{ label: "normal" },
|
||||||
|
{ label: "bold" },
|
||||||
|
{ label: "bolder" },
|
||||||
|
{ label: "lighter" },
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{ label: "size", key: "font-size", defaultValue: "", control: Input },
|
||||||
|
{ label: "Line H", key: "line-height", control: Input },
|
||||||
|
{
|
||||||
|
label: "Color",
|
||||||
|
key: "color",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: ["black", "white", "red", "blue", "green"],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "align",
|
||||||
|
key: "text-align",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: ["initial", "left", "right", "center", "justify"],
|
||||||
|
}, //custom
|
||||||
|
{ label: "transform", key: "text-transform", control: Input }, //custom
|
||||||
|
{ label: "style", key: "font-style", control: Input }, //custom
|
||||||
|
]
|
||||||
|
|
||||||
|
export const background = [
|
||||||
|
{
|
||||||
|
label: "Background",
|
||||||
|
key: "background",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: ["black", "white", "red", "blue", "green"],
|
||||||
|
},
|
||||||
|
{ label: "Image", key: "image", control: Input }, //custom
|
||||||
|
]
|
||||||
|
|
||||||
|
export const border = [
|
||||||
|
{ label: "Radius", key: "border-radius", control: Input },
|
||||||
|
{ label: "Width", key: "border-width", control: Input }, //custom
|
||||||
|
{
|
||||||
|
label: "Color",
|
||||||
|
key: "border-color",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: ["black", "white", "red", "blue", "green"],
|
||||||
|
},
|
||||||
|
{ label: "Style", key: "border-style", control: Input },
|
||||||
|
]
|
||||||
|
|
||||||
|
export const effects = [
|
||||||
|
{ label: "Opacity", key: "opacity", control: Input },
|
||||||
|
{ label: "Rotate", key: "transform", control: Input }, //needs special control
|
||||||
|
{ label: "Shadow", key: "box-shadow", control: Input },
|
||||||
|
]
|
||||||
|
|
||||||
|
export const transitions = [
|
||||||
|
{ label: "Property", key: "transition-property", control: Input },
|
||||||
|
{ label: "Duration", key: "transition-timing-function", control: Input },
|
||||||
|
{ label: "Ease", key: "transition-ease", control: Input },
|
||||||
|
]
|
||||||
|
|
||||||
|
export const all = {
|
||||||
|
layout,
|
||||||
|
spacing,
|
||||||
|
size,
|
||||||
|
position,
|
||||||
|
typography,
|
||||||
|
background,
|
||||||
|
border,
|
||||||
|
effects,
|
||||||
|
transitions,
|
||||||
|
}
|
||||||
|
|
||||||
|
export function excludeProps(props, propsToExclude) {
|
||||||
|
const modifiedProps = {}
|
||||||
|
for (const prop in props) {
|
||||||
|
if (!propsToExclude.includes(prop)) {
|
||||||
|
modifiedProps[prop] = props[prop]
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return modifiedProps
|
||||||
|
}
|
|
@ -1,3 +1,9 @@
|
||||||
|
import Input from "../common/Input.svelte"
|
||||||
|
import OptionSelect from "./OptionSelect.svelte"
|
||||||
|
import Checkbox from "../common/Checkbox.svelte"
|
||||||
|
|
||||||
|
import { all } from "./propertyCategories.js"
|
||||||
|
|
||||||
export default {
|
export default {
|
||||||
categories: [
|
categories: [
|
||||||
{
|
{
|
||||||
|
@ -20,6 +26,31 @@ export default {
|
||||||
icon: "ri-layout-row-fill",
|
icon: "ri-layout-row-fill",
|
||||||
commonProps: {},
|
commonProps: {},
|
||||||
children: [],
|
children: [],
|
||||||
|
properties: {
|
||||||
|
design: { ...all },
|
||||||
|
settings: [
|
||||||
|
{
|
||||||
|
key: "type",
|
||||||
|
label: "Type",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: [
|
||||||
|
{ label: "article" },
|
||||||
|
{ label: "aside" },
|
||||||
|
{ label: "details" },
|
||||||
|
{ label: "div" },
|
||||||
|
{ label: "figure" },
|
||||||
|
{ label: "figcaption" },
|
||||||
|
{ label: "footer" },
|
||||||
|
{ label: "header" },
|
||||||
|
{ label: "main" },
|
||||||
|
{ label: "mark" },
|
||||||
|
{ label: "nav" },
|
||||||
|
{ label: "paragraph" },
|
||||||
|
{ label: "summary" },
|
||||||
|
],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "Text",
|
name: "Text",
|
||||||
|
@ -32,13 +63,21 @@ export default {
|
||||||
name: "Headline",
|
name: "Headline",
|
||||||
description: "A component for displaying heading text",
|
description: "A component for displaying heading text",
|
||||||
icon: "ri-heading",
|
icon: "ri-heading",
|
||||||
props: {
|
properties: {
|
||||||
type: {
|
design: { ...all },
|
||||||
type: "options",
|
settings: [
|
||||||
options: ["h1", "h2", "h3", "h4", "h5", "h6"],
|
{
|
||||||
default: "h1",
|
key: "text",
|
||||||
|
label: "Text",
|
||||||
|
control: Input,
|
||||||
},
|
},
|
||||||
text: "string",
|
{
|
||||||
|
key: "type",
|
||||||
|
label: "Type",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: ["h1", "h2", "h3", "h4", "h5", "h6"],
|
||||||
|
},
|
||||||
|
],
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -46,7 +85,34 @@ export default {
|
||||||
name: "Paragraph",
|
name: "Paragraph",
|
||||||
description: "A component for displaying paragraph text.",
|
description: "A component for displaying paragraph text.",
|
||||||
icon: "ri-paragraph",
|
icon: "ri-paragraph",
|
||||||
props: {},
|
properties: {
|
||||||
|
design: { ...all },
|
||||||
|
settings: [
|
||||||
|
{
|
||||||
|
label: "Text",
|
||||||
|
key: "text",
|
||||||
|
control: Input,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: "Type",
|
||||||
|
key: "type",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: [
|
||||||
|
"none",
|
||||||
|
"bold",
|
||||||
|
"strong",
|
||||||
|
"italic",
|
||||||
|
"emphasis",
|
||||||
|
"mark",
|
||||||
|
"small",
|
||||||
|
"del",
|
||||||
|
"ins",
|
||||||
|
"sub",
|
||||||
|
"sup",
|
||||||
|
],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
@ -62,21 +128,38 @@ export default {
|
||||||
description:
|
description:
|
||||||
"A textfield component that allows the user to input text.",
|
"A textfield component that allows the user to input text.",
|
||||||
icon: "ri-edit-box-line",
|
icon: "ri-edit-box-line",
|
||||||
props: {},
|
properties: {
|
||||||
|
design: { ...all },
|
||||||
|
settings: [
|
||||||
|
{ label: "Label", key: "label", control: Input },
|
||||||
|
{
|
||||||
|
label: "Type",
|
||||||
|
key: "type",
|
||||||
|
control: OptionSelect,
|
||||||
|
options: ["text", "password"],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
_component: "@budibase/standard-components/checkbox",
|
_component: "@budibase/standard-components/checkbox",
|
||||||
name: "Checkbox",
|
name: "Checkbox",
|
||||||
description: "A selectable checkbox component",
|
description: "A selectable checkbox component",
|
||||||
icon: "ri-checkbox-line",
|
icon: "ri-checkbox-line",
|
||||||
props: {},
|
properties: {
|
||||||
|
design: { ...all },
|
||||||
|
settings: [{ label: "Label", key: "label", control: Input }],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
_component: "@budibase/standard-components/radiobutton",
|
_component: "@budibase/standard-components/radiobutton",
|
||||||
name: "Radiobutton",
|
name: "Radiobutton",
|
||||||
description: "A selectable radiobutton component",
|
description: "A selectable radiobutton component",
|
||||||
icon: "ri-radio-button-line",
|
icon: "ri-radio-button-line",
|
||||||
props: {},
|
properties: {
|
||||||
|
design: { ...all },
|
||||||
|
settings: [{ label: "Label", key: "label", control: Input }],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
_component: "@budibase/standard-components/select",
|
_component: "@budibase/standard-components/select",
|
||||||
|
@ -84,7 +167,10 @@ export default {
|
||||||
description:
|
description:
|
||||||
"A select component for choosing from different options",
|
"A select component for choosing from different options",
|
||||||
icon: "ri-file-list-line",
|
icon: "ri-file-list-line",
|
||||||
props: {},
|
properties: {
|
||||||
|
design: { ...all },
|
||||||
|
settings: [],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
@ -93,24 +179,51 @@ export default {
|
||||||
name: "Button",
|
name: "Button",
|
||||||
description: "A basic html button that is ready for styling",
|
description: "A basic html button that is ready for styling",
|
||||||
icon: "ri-radio-button-fill",
|
icon: "ri-radio-button-fill",
|
||||||
commonProps: {},
|
|
||||||
children: [],
|
children: [],
|
||||||
|
properties: {
|
||||||
|
design: {
|
||||||
|
...all,
|
||||||
|
},
|
||||||
|
settings: [
|
||||||
|
{ label: "Text", key: "text", control: Input },
|
||||||
|
{
|
||||||
|
label: "Disabled",
|
||||||
|
key: "disabled",
|
||||||
|
valueKey: "checked",
|
||||||
|
control: Checkbox,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
_component: "@budibase/standard-components/icon",
|
_component: "@budibase/standard-components/icon",
|
||||||
name: "Icon",
|
name: "Icon",
|
||||||
description: "A basic component for displaying icons",
|
description: "A basic component for displaying icons",
|
||||||
icon: "ri-sun-fill",
|
icon: "ri-sun-fill",
|
||||||
commonProps: {},
|
|
||||||
children: [],
|
children: [],
|
||||||
|
properties: {
|
||||||
|
design: { ...all },
|
||||||
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
_component: "@budibase/standard-components/link",
|
_component: "@budibase/standard-components/link",
|
||||||
name: "Link",
|
name: "Link",
|
||||||
description: "A basic link component for internal and external links",
|
description: "A basic link component for internal and external links",
|
||||||
icon: "ri-link",
|
icon: "ri-link",
|
||||||
commonProps: {},
|
|
||||||
children: [],
|
children: [],
|
||||||
|
properties: {
|
||||||
|
design: { ...all },
|
||||||
|
settings: [
|
||||||
|
{ label: "Text", key: "text", control: Input },
|
||||||
|
{ label: "Url", key: "url", control: Input },
|
||||||
|
{
|
||||||
|
label: "Open New Tab",
|
||||||
|
key: "openInNewTab",
|
||||||
|
valueKey: "checked",
|
||||||
|
control: Checkbox,
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
@ -124,17 +237,16 @@ export default {
|
||||||
description:
|
description:
|
||||||
"A basic card component that can contain content and actions.",
|
"A basic card component that can contain content and actions.",
|
||||||
icon: "ri-layout-bottom-line",
|
icon: "ri-layout-bottom-line",
|
||||||
commonProps: {},
|
|
||||||
children: [],
|
children: [],
|
||||||
|
properties: { design: { ...all } },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
_component: "@budibase/standard-components/login",
|
|
||||||
name: "Login",
|
name: "Login",
|
||||||
description:
|
description:
|
||||||
"A component that automatically generates a login screen for your app.",
|
"A component that automatically generates a login screen for your app.",
|
||||||
icon: "ri-login-box-fill",
|
icon: "ri-login-box-fill",
|
||||||
commonProps: {},
|
|
||||||
children: [],
|
children: [],
|
||||||
|
properties: { design: { ...all } },
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "Navigation Bar",
|
name: "Navigation Bar",
|
||||||
|
@ -142,8 +254,8 @@ export default {
|
||||||
description:
|
description:
|
||||||
"A component for handling the navigation within your app.",
|
"A component for handling the navigation within your app.",
|
||||||
icon: "ri-navigation-fill",
|
icon: "ri-navigation-fill",
|
||||||
commonProps: {},
|
|
||||||
children: [],
|
children: [],
|
||||||
|
properties: { design: { ...all } },
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
@ -153,19 +265,17 @@ export default {
|
||||||
children: [
|
children: [
|
||||||
{
|
{
|
||||||
name: "Table",
|
name: "Table",
|
||||||
_component: "@budibase/materialdesign-components/Datatable",
|
|
||||||
description: "A component that generates a table from your data.",
|
description: "A component that generates a table from your data.",
|
||||||
icon: "ri-archive-drawer-fill",
|
icon: "ri-archive-drawer-fill",
|
||||||
commonProps: {},
|
properties: { design: { ...all } },
|
||||||
children: [],
|
children: [],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
_component: "@budibase/materialdesign-components/Form",
|
|
||||||
name: "Form",
|
name: "Form",
|
||||||
description: "A component that generates a form from your data.",
|
description: "A component that generates a form from your data.",
|
||||||
icon: "ri-file-edit-fill",
|
icon: "ri-file-edit-fill",
|
||||||
commonProps: {},
|
properties: { design: { ...all } },
|
||||||
component: "@budibase/materialdesign-components/Form",
|
_component: "@budibase/materialdesign-components/Form",
|
||||||
template: {
|
template: {
|
||||||
component: "@budibase/materialdesign-components/Form",
|
component: "@budibase/materialdesign-components/Form",
|
||||||
description: "Form for saving a record",
|
description: "Form for saving a record",
|
||||||
|
@ -178,7 +288,7 @@ export default {
|
||||||
name: "DataTable",
|
name: "DataTable",
|
||||||
description: "A table for displaying data from the backend.",
|
description: "A table for displaying data from the backend.",
|
||||||
icon: "ri-archive-drawer-fill",
|
icon: "ri-archive-drawer-fill",
|
||||||
commonProps: {},
|
properties: { design: { ...all } },
|
||||||
children: [],
|
children: [],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -186,7 +296,7 @@ export default {
|
||||||
name: "DataForm",
|
name: "DataForm",
|
||||||
description: "Form stuff",
|
description: "Form stuff",
|
||||||
icon: "ri-file-edit-fill",
|
icon: "ri-file-edit-fill",
|
||||||
commonProps: {},
|
properties: { design: { ...all } },
|
||||||
children: [],
|
children: [],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -194,7 +304,7 @@ export default {
|
||||||
_component: "@budibase/standard-components/datachart",
|
_component: "@budibase/standard-components/datachart",
|
||||||
description: "Shiny chart",
|
description: "Shiny chart",
|
||||||
icon: "ri-bar-chart-line",
|
icon: "ri-bar-chart-line",
|
||||||
commonProps: {},
|
properties: { design: { ...all } },
|
||||||
children: [],
|
children: [],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -202,7 +312,7 @@ export default {
|
||||||
_component: "@budibase/standard-components/datalist",
|
_component: "@budibase/standard-components/datalist",
|
||||||
description: "Shiny list",
|
description: "Shiny list",
|
||||||
icon: "ri-file-list-line",
|
icon: "ri-file-list-line",
|
||||||
commonProps: {},
|
properties: { design: { ...all } },
|
||||||
children: [],
|
children: [],
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -210,7 +320,7 @@ export default {
|
||||||
_component: "@budibase/standard-components/datamap",
|
_component: "@budibase/standard-components/datamap",
|
||||||
description: "Shiny map",
|
description: "Shiny map",
|
||||||
icon: "ri-map-pin-line",
|
icon: "ri-map-pin-line",
|
||||||
commonProps: {},
|
properties: { design: { ...all } },
|
||||||
children: [],
|
children: [],
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
|
|
|
@ -1,5 +1,20 @@
|
||||||
|
|
||||||
:root {
|
:root {
|
||||||
|
|
||||||
|
--white: #FFFFFF;
|
||||||
|
|
||||||
|
--blue: #0055ff;
|
||||||
|
--blue-light: #F1F4FC;
|
||||||
|
--blue-dark: #2F4C9B;
|
||||||
|
|
||||||
|
--ink: #393C44;
|
||||||
|
--ink-light: #808192;
|
||||||
|
--ink-lighter: #ADAEC4;
|
||||||
|
|
||||||
|
--grey: #F2F2F2;
|
||||||
|
--grey-light: #FBFBFB;
|
||||||
|
--grey-dark: #E6E6E6;
|
||||||
|
|
||||||
--primary100: #0055ff;
|
--primary100: #0055ff;
|
||||||
--primary80: rgba(0, 85, 255, 0.8);
|
--primary80: rgba(0, 85, 255, 0.8);
|
||||||
--primary60: #rgba(0, 85, 255, 0.6);
|
--primary60: #rgba(0, 85, 255, 0.6);
|
||||||
|
@ -9,7 +24,7 @@
|
||||||
--primary5: #rgba(0, 85, 255, 0.05);
|
--primary5: #rgba(0, 85, 255, 0.05);
|
||||||
--primarydark: #0044cc;
|
--primarydark: #0044cc;
|
||||||
|
|
||||||
--secondary100:#000333;
|
--secondary100:#393C44;
|
||||||
--secondary80: rgba(0, 3, 51, 0.8);
|
--secondary80: rgba(0, 3, 51, 0.8);
|
||||||
--secondary60: rgba(0, 3, 51, 0.6);
|
--secondary60: rgba(0, 3, 51, 0.6);
|
||||||
--secondary40: rgba(0, 3, 51, 0.4);
|
--secondary40: rgba(0, 3, 51, 0.4);
|
||||||
|
@ -34,7 +49,7 @@
|
||||||
--deletion10: #F2545B1A;
|
--deletion10: #F2545B1A;
|
||||||
--deletiondark: #CF4046;
|
--deletiondark: #CF4046;
|
||||||
|
|
||||||
--white: #FFFFFF;
|
|
||||||
--darkslate: #1a202c;
|
--darkslate: #1a202c;
|
||||||
--slate: #d8d8d8;
|
--slate: #d8d8d8;
|
||||||
--lightslate: #f9f9f9;
|
--lightslate: #f9f9f9;
|
||||||
|
@ -105,7 +120,7 @@ h3 {
|
||||||
h4 {
|
h4 {
|
||||||
font-family: var(--fontbold);
|
font-family: var(--fontbold);
|
||||||
font-size: 18pt;
|
font-size: 18pt;
|
||||||
color: var(--secondary100);
|
color: var(--ink);
|
||||||
}
|
}
|
||||||
|
|
||||||
h5 {
|
h5 {
|
||||||
|
|
|
@ -10,18 +10,15 @@
|
||||||
|
|
||||||
<link rel='icon' type='image/png' href='/_builder/favicon.png'>
|
<link rel='icon' type='image/png' href='/_builder/favicon.png'>
|
||||||
<link rel='stylesheet' href='/_builder/global.css'>
|
<link rel='stylesheet' href='/_builder/global.css'>
|
||||||
<link rel='stylesheet' href='/_builder/flowy.css'>
|
|
||||||
<link rel='stylesheet' href='/_builder/codemirror.css'>
|
<link rel='stylesheet' href='/_builder/codemirror.css'>
|
||||||
<link rel='stylesheet' href='/_builder/budibase.css'>
|
<link rel='stylesheet' href='/_builder/budibase.css'>
|
||||||
<link rel='stylesheet' href='/_builder/monokai.css'>
|
<link rel='stylesheet' href='/_builder/monokai.css'>
|
||||||
<link rel='stylesheet' href='/_builder/bundle.css'>
|
<link rel='stylesheet' href='/_builder/bundle.css'>
|
||||||
<link rel='stylesheet' href='/_builder/fonts.css'>
|
<link rel='stylesheet' href='/_builder/fonts.css'>
|
||||||
<link rel='stylesheet' href="/_builder/uikit.min.css">
|
<link rel='stylesheet' href="/_builder/uikit.min.css">
|
||||||
<link rel="stylesheet" href="https://cdn.jsdelivr.net/gh/alyssaxuu/flowy/flowy.min.css">
|
|
||||||
</head>
|
</head>
|
||||||
|
|
||||||
<body id="app">
|
<body id="app">
|
||||||
<script src="https://cdn.jsdelivr.net/gh/alyssaxuu/flowy/flowy.min.js"></script>
|
|
||||||
<script src='/_builder/bundle.js'></script>
|
<script src='/_builder/bundle.js'></script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
|
@ -1,5 +1,4 @@
|
||||||
import "./global.css"
|
import "./global.css"
|
||||||
import "./flowy.css";
|
|
||||||
import "./fonts.css"
|
import "./fonts.css"
|
||||||
import "./budibase.css"
|
import "./budibase.css"
|
||||||
import "/assets/roboto-v20-latin-ext_latin-300"
|
import "/assets/roboto-v20-latin-ext_latin-300"
|
||||||
|
|
|
@ -31,8 +31,9 @@
|
||||||
<div class="topleftnav">
|
<div class="topleftnav">
|
||||||
<button class="home-logo">
|
<button class="home-logo">
|
||||||
<img
|
<img
|
||||||
src="/_builder/assets/budibase-emblem-white.svg"
|
src="/_builder/assets/bb-logo.svg"
|
||||||
alt="budibase icon" />
|
alt="budibase icon"
|
||||||
|
on:click={() => $goto(`/`)} />
|
||||||
</button>
|
</button>
|
||||||
|
|
||||||
<!-- This gets all indexable subroutes and sticks them in the top nav. -->
|
<!-- This gets all indexable subroutes and sticks them in the top nav. -->
|
||||||
|
@ -85,13 +86,14 @@
|
||||||
|
|
||||||
.top-nav {
|
.top-nav {
|
||||||
flex: 0 0 auto;
|
flex: 0 0 auto;
|
||||||
height: 48px;
|
height: 60px;
|
||||||
background: #0d203b;
|
background: #fff;
|
||||||
padding: 0px 20px 0 20px;
|
padding: 0px 20px 0 20px;
|
||||||
display: flex;
|
display: flex;
|
||||||
box-sizing: border-box;
|
box-sizing: border-box;
|
||||||
justify-content: space-between;
|
justify-content: space-between;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
|
border-bottom: 1px solid var(--grey);
|
||||||
}
|
}
|
||||||
|
|
||||||
.content > div {
|
.content > div {
|
||||||
|
@ -110,8 +112,8 @@
|
||||||
|
|
||||||
.topnavitem {
|
.topnavitem {
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
color: rgb(255, 255, 255, 0.6);
|
color: var(--ink-lighter);
|
||||||
margin: 0px 10px;
|
margin: 0px 00px 0px 20px;
|
||||||
padding-top: 4px;
|
padding-top: 4px;
|
||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
font-size: 1rem;
|
font-size: 1rem;
|
||||||
|
@ -121,19 +123,19 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
.topnavitem:hover {
|
.topnavitem:hover {
|
||||||
color: rgb(255, 255, 255, 0.8);
|
color: var(--ink-light);
|
||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
}
|
}
|
||||||
|
|
||||||
.active {
|
.active {
|
||||||
color: white;
|
color: var(--ink);
|
||||||
font-weight: 600;
|
font-weight: 500;
|
||||||
}
|
}
|
||||||
|
|
||||||
.topnavitemright {
|
.topnavitemright {
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
color: rgb(255, 255, 255, 0.6);
|
color: var(--ink-light);
|
||||||
margin: 0px 5px;
|
margin: 0px 20px 0px 0px;
|
||||||
padding-top: 4px;
|
padding-top: 4px;
|
||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
font-size: 1rem;
|
font-size: 1rem;
|
||||||
|
@ -155,7 +157,8 @@
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
outline: none;
|
outline: none;
|
||||||
height: 40px;
|
height: 40px;
|
||||||
padding: 8px 10px 8px 0;
|
padding: 0px 10px 8px 0;
|
||||||
|
align-items: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
.home-logo:hover {
|
.home-logo:hover {
|
||||||
|
@ -167,7 +170,7 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
.home-logo img {
|
.home-logo img {
|
||||||
height: 100%;
|
height: 40px;
|
||||||
}
|
}
|
||||||
span:first-letter {
|
span:first-letter {
|
||||||
text-transform: capitalize;
|
text-transform: capitalize;
|
||||||
|
|
|
@ -37,4 +37,13 @@
|
||||||
width: 275px;
|
width: 275px;
|
||||||
height: 100%;
|
height: 100%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@media only screen and (min-width: 1800px) {
|
||||||
|
.nav {
|
||||||
|
overflow: auto;
|
||||||
|
flex: 0 1 auto;
|
||||||
|
width: 300px;
|
||||||
|
height: 100%;
|
||||||
|
}
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
|
@ -54,9 +54,7 @@
|
||||||
|
|
||||||
<div class="pages-list-container">
|
<div class="pages-list-container">
|
||||||
<div class="nav-header">
|
<div class="nav-header">
|
||||||
<span class="navigator-title">Navigator</span>
|
<span class="navigator-title">Navigate</span>
|
||||||
<div class="border-line" />
|
|
||||||
|
|
||||||
<span class="components-nav-page">Pages</span>
|
<span class="components-nav-page">Pages</span>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
@ -129,18 +127,16 @@
|
||||||
.root {
|
.root {
|
||||||
display: grid;
|
display: grid;
|
||||||
grid-template-columns: 275px 1fr 275px;
|
grid-template-columns: 275px 1fr 275px;
|
||||||
height: 100%;
|
|
||||||
width: 100%;
|
width: 100%;
|
||||||
background: #fafafa;
|
background: var(--grey-light);
|
||||||
}
|
}
|
||||||
|
|
||||||
@media only screen and (min-width: 1800px) {
|
@media only screen and (min-width: 1800px) {
|
||||||
.root {
|
.root {
|
||||||
display: grid;
|
display: grid;
|
||||||
grid-template-columns: 300px 1fr 300px;
|
grid-template-columns: 300px 1fr 300px;
|
||||||
height: 100%;
|
|
||||||
width: 100%;
|
width: 100%;
|
||||||
background: #fafafa;
|
background: var(--grey-light);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -159,20 +155,16 @@
|
||||||
margin: 40px;
|
margin: 40px;
|
||||||
background: #fff;
|
background: #fff;
|
||||||
border-radius: 5px;
|
border-radius: 5px;
|
||||||
box-shadow: 0 0px 6px rgba(0, 0, 0, 0.05);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.components-pane {
|
.components-pane {
|
||||||
grid-column: 3;
|
grid-column: 3;
|
||||||
background-color: var(--white);
|
background-color: var(--white);
|
||||||
min-height: 0px;
|
|
||||||
overflow-y: scroll;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.components-nav-page {
|
.components-nav-page {
|
||||||
font-size: 13px;
|
font-size: 13px;
|
||||||
color: #000333;
|
color: var(--ink);
|
||||||
text-transform: uppercase;
|
|
||||||
padding-left: 20px;
|
padding-left: 20px;
|
||||||
margin-top: 20px;
|
margin-top: 20px;
|
||||||
font-weight: 600;
|
font-weight: 600;
|
||||||
|
@ -182,8 +174,7 @@
|
||||||
|
|
||||||
.components-nav-header {
|
.components-nav-header {
|
||||||
font-size: 13px;
|
font-size: 13px;
|
||||||
color: #000333;
|
color: var(--ink);
|
||||||
text-transform: uppercase;
|
|
||||||
margin-top: 20px;
|
margin-top: 20px;
|
||||||
font-weight: 600;
|
font-weight: 600;
|
||||||
opacity: 0.4;
|
opacity: 0.4;
|
||||||
|
@ -235,13 +226,10 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
.navigator-title {
|
.navigator-title {
|
||||||
font-size: 14px;
|
font-size: 18px;
|
||||||
color: var(--secondary100);
|
color: var(--ink);
|
||||||
font-weight: 600;
|
font-weight: bold;
|
||||||
text-transform: uppercase;
|
|
||||||
padding: 0 20px 20px 20px;
|
padding: 0 20px 20px 20px;
|
||||||
line-height: 1rem !important;
|
|
||||||
letter-spacing: 1px;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
.border-line {
|
.border-line {
|
||||||
|
|
|
@ -1 +0,0 @@
|
||||||
export { default as BlockPanel } from "./BlockPanel.svelte";
|
|
|
@ -0,0 +1,88 @@
|
||||||
|
<script>
|
||||||
|
import { onMount } from "svelte"
|
||||||
|
import { backendUiStore, workflowStore } from "builderStore"
|
||||||
|
import api from "builderStore/api"
|
||||||
|
import WorkflowBlockSetup from "./WorkflowBlockSetup.svelte";
|
||||||
|
|
||||||
|
$: workflow = $workflowStore.workflows.find(
|
||||||
|
wf => wf._id === $workflowStore.selectedWorkflowId
|
||||||
|
)
|
||||||
|
$: workflowBlock = $workflowStore.selectedWorkflowBlock
|
||||||
|
|
||||||
|
function deleteWorkflow() {
|
||||||
|
workflowStore.actions.deleteWorkflow(workflow)
|
||||||
|
}
|
||||||
|
|
||||||
|
function deleteWorkflowBlock() {
|
||||||
|
// TODO: implement
|
||||||
|
workflowStore.actions.deleteWorkflowBlock(workflowBlock)
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<header>
|
||||||
|
<span>Setup</span>
|
||||||
|
</header>
|
||||||
|
<div class="panel-body">
|
||||||
|
{#if workflowBlock}
|
||||||
|
<WorkflowBlockSetup {workflowBlock} />
|
||||||
|
<button class="delete-workflow-button hoverable" on:click={deleteWorkflowBlock}>
|
||||||
|
Delete {workflowBlock.type}
|
||||||
|
</button>
|
||||||
|
{:else if $workflowStore.selectedWorkflowId}
|
||||||
|
<label class="uk-form-label">Workflow: {workflow.name}</label>
|
||||||
|
<div class="uk-margin">
|
||||||
|
<label class="uk-form-label">Name</label>
|
||||||
|
<div class="uk-form-controls">
|
||||||
|
<input
|
||||||
|
type="text"
|
||||||
|
class="budibase__input"
|
||||||
|
bind:value={workflow.name} />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="uk-margin">
|
||||||
|
<label class="uk-form-label">User Access</label>
|
||||||
|
Some User Access Stuff Here
|
||||||
|
</div>
|
||||||
|
<button class="delete-workflow-button hoverable" on:click={deleteWorkflow}>
|
||||||
|
Delete Workflow
|
||||||
|
</button>
|
||||||
|
{/if}
|
||||||
|
</div>
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
section {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
}
|
||||||
|
|
||||||
|
header {
|
||||||
|
font-size: 20px;
|
||||||
|
font-weight: bold;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
}
|
||||||
|
|
||||||
|
span:not(.selected) {
|
||||||
|
color: var(--dark-grey);
|
||||||
|
}
|
||||||
|
|
||||||
|
label {
|
||||||
|
font-weight: 500;
|
||||||
|
font-size: 14px;
|
||||||
|
color: var(--font);
|
||||||
|
}
|
||||||
|
|
||||||
|
.delete-workflow-button {
|
||||||
|
font-family: Roboto;
|
||||||
|
width: 100%;
|
||||||
|
border: solid 1px #f2f2f2;
|
||||||
|
border-radius: 2px;
|
||||||
|
background: var(--white);
|
||||||
|
height: 32px;
|
||||||
|
font-size: 12px;
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -0,0 +1,17 @@
|
||||||
|
<script>
|
||||||
|
export let workflowBlock
|
||||||
|
$: workflowArgs = Object.keys(workflowBlock.args)
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<label class="uk-form-label">{workflowBlock.heading}: {workflowBlock.heading}</label>
|
||||||
|
{#each workflowArgs as workflowArg}
|
||||||
|
<div class="uk-margin">
|
||||||
|
<label class="uk-form-label">Name</label>
|
||||||
|
<div class="uk-form-controls">
|
||||||
|
<input
|
||||||
|
type="text"
|
||||||
|
class="budibase__input"
|
||||||
|
bind:value={workflowBlock.args[workflowArg]} />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
{/each}
|
|
@ -0,0 +1 @@
|
||||||
|
export { default as SetupPanel } from "./SetupPanel.svelte";
|
|
@ -0,0 +1,51 @@
|
||||||
|
<script>
|
||||||
|
import { onMount } from "svelte"
|
||||||
|
import { workflowStore, backendUiStore } from "builderStore"
|
||||||
|
import Flowchart from "./svelte-flows/Flowchart.svelte"
|
||||||
|
import api from "builderStore/api"
|
||||||
|
|
||||||
|
let canvas
|
||||||
|
let workflow
|
||||||
|
let uiTree
|
||||||
|
let instanceId = $backendUiStore.selectedDatabase._id
|
||||||
|
|
||||||
|
$: workflow = $workflowStore.workflows.find(
|
||||||
|
wf => wf._id === $workflowStore.selectedWorkflowId
|
||||||
|
)
|
||||||
|
|
||||||
|
// Build a renderable UI Tree for the flowchart generator
|
||||||
|
function buildUiTree(block, tree = []) {
|
||||||
|
if (!block) return tree
|
||||||
|
|
||||||
|
tree.push({
|
||||||
|
type: block.type,
|
||||||
|
heading: block.actionId,
|
||||||
|
args: block.args,
|
||||||
|
body: JSON.stringify(block.args),
|
||||||
|
})
|
||||||
|
|
||||||
|
return buildUiTree(block.next, tree)
|
||||||
|
}
|
||||||
|
|
||||||
|
$: if (workflow) uiTree = workflow.definition ? buildUiTree(workflow.definition.next) : []
|
||||||
|
|
||||||
|
function onDelete(block) {
|
||||||
|
// TODO finish
|
||||||
|
workflowStore.actions.deleteWorkflowBlock(block);
|
||||||
|
}
|
||||||
|
|
||||||
|
function onSelect(block) {
|
||||||
|
workflowStore.update(state => {
|
||||||
|
state.selectedWorkflowBlock = block
|
||||||
|
return state
|
||||||
|
})
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<Flowchart
|
||||||
|
blocks={uiTree}
|
||||||
|
onSelect={onSelect}
|
||||||
|
on:delete={onDelete}
|
||||||
|
/>
|
||||||
|
</section>
|
|
@ -0,0 +1,23 @@
|
||||||
|
<script>
|
||||||
|
import FlowItem from "./FlowItem.svelte"
|
||||||
|
|
||||||
|
export let blocks = []
|
||||||
|
export let onSelect
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<section class="canvas">
|
||||||
|
{#each blocks as block, idx}
|
||||||
|
<FlowItem onSelect={onSelect} {block} />
|
||||||
|
{#if idx !== blocks.length - 1}
|
||||||
|
<i class="ri-arrow-down-line"></i>
|
||||||
|
{/if}
|
||||||
|
{/each}
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.canvas {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
flex-direction: column;
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -0,0 +1,33 @@
|
||||||
|
<script>
|
||||||
|
export let onSelect
|
||||||
|
export let block
|
||||||
|
|
||||||
|
function selectBlock() {
|
||||||
|
onSelect(block);
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="hoverable" on:click={selectBlock}>
|
||||||
|
<header>{block.heading}</header>
|
||||||
|
<hr />
|
||||||
|
<p>{block.body}</p>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
div {
|
||||||
|
border: 1px solid black;
|
||||||
|
width: 320px;
|
||||||
|
padding: 20px;
|
||||||
|
margin-bottom: 60px;
|
||||||
|
border-radius: 5px;
|
||||||
|
transition: 0.3s all;
|
||||||
|
box-shadow: 0 4px 30px 0 rgba(57, 60, 68, 0.08);
|
||||||
|
background-color: var(--font);
|
||||||
|
font-size: 16px;
|
||||||
|
color: var(--white);
|
||||||
|
}
|
||||||
|
|
||||||
|
div:hover {
|
||||||
|
transform: scale(1.05);
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -1 +0,0 @@
|
||||||
export { default as WorkflowList } from "./WorkflowList.svelte";
|
|
|
@ -1,8 +1,10 @@
|
||||||
<script>
|
<script>
|
||||||
import { onMount } from "svelte"
|
import { onMount } from "svelte"
|
||||||
import { backendUiStore } from "builderStore"
|
import { backendUiStore } from "builderStore"
|
||||||
|
import { WorkflowList } from "../";
|
||||||
|
import WorkflowBlock from "./WorkflowBlock.svelte";
|
||||||
import api from "builderStore/api"
|
import api from "builderStore/api"
|
||||||
import blockDefinitions from "./blockDefinitions"
|
import blockDefinitions from "../blockDefinitions"
|
||||||
|
|
||||||
const SUB_TABS = [
|
const SUB_TABS = [
|
||||||
{
|
{
|
||||||
|
@ -14,8 +16,8 @@
|
||||||
key: "ACTIONS",
|
key: "ACTIONS",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "Utilities",
|
name: "Logic",
|
||||||
key: "UTILITIES",
|
key: "LOGIC",
|
||||||
},
|
},
|
||||||
]
|
]
|
||||||
|
|
||||||
|
@ -23,13 +25,13 @@
|
||||||
let definitions = []
|
let definitions = []
|
||||||
|
|
||||||
$: definitions = Object.values(blockDefinitions[selectedTab])
|
$: definitions = Object.values(blockDefinitions[selectedTab])
|
||||||
|
|
||||||
|
function myAction(node) {
|
||||||
|
console.log("ACTION FIRED", node);
|
||||||
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<section>
|
<section>
|
||||||
<header>
|
|
||||||
<span>Blocks</span>
|
|
||||||
<span>Props</span>
|
|
||||||
</header>
|
|
||||||
<div class="subtabs">
|
<div class="subtabs">
|
||||||
{#each SUB_TABS as tab}
|
{#each SUB_TABS as tab}
|
||||||
<span
|
<span
|
||||||
|
@ -42,38 +44,12 @@
|
||||||
</div>
|
</div>
|
||||||
<div id="blocklist">
|
<div id="blocklist">
|
||||||
{#each definitions as blockDefinition}
|
{#each definitions as blockDefinition}
|
||||||
<div
|
<WorkflowBlock {blockDefinition} blockType={selectedTab} />
|
||||||
class="blockelem create-flowy noselect"
|
|
||||||
data-name={blockDefinition.name}
|
|
||||||
>
|
|
||||||
<input
|
|
||||||
type="hidden"
|
|
||||||
name="blockelemtype"
|
|
||||||
class="blockelemtype"
|
|
||||||
value="1" />
|
|
||||||
<div class="blockin">
|
|
||||||
<div class="blockico">
|
|
||||||
<i class={blockDefinition.icon} />
|
|
||||||
</div>
|
|
||||||
<div class="blocktext">
|
|
||||||
<p class="blocktitle">{blockDefinition.name}</p>
|
|
||||||
<p class="blockdesc">{blockDefinition.description}</p>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
{/each}
|
{/each}
|
||||||
</div>
|
</div>
|
||||||
</section>
|
</section>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
header {
|
|
||||||
font-size: 20px;
|
|
||||||
font-weight: bold;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: space-between;
|
|
||||||
}
|
|
||||||
|
|
||||||
.subtabs {
|
.subtabs {
|
||||||
margin-top: 27px;
|
margin-top: 27px;
|
||||||
display: grid;
|
display: grid;
|
|
@ -0,0 +1,51 @@
|
||||||
|
<script>
|
||||||
|
import { workflowStore } from "builderStore";
|
||||||
|
|
||||||
|
export let blockType
|
||||||
|
export let blockDefinition
|
||||||
|
|
||||||
|
function addBlockToWorkflow() {
|
||||||
|
// TODO: store the block type in the DB as well
|
||||||
|
workflowStore.actions.addBlockToWorkflow({ blockDefinition, blockType });
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<div class="workflow-block hoverable" on:click={addBlockToWorkflow}>
|
||||||
|
<div>
|
||||||
|
<i class={blockDefinition.icon} />
|
||||||
|
</div>
|
||||||
|
<div class="workflow-text">
|
||||||
|
<h4>{blockDefinition.name}</h4>
|
||||||
|
<p>{blockDefinition.description}</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
.workflow-block {
|
||||||
|
display: flex;
|
||||||
|
padding: 20px;
|
||||||
|
align-items: center;
|
||||||
|
}
|
||||||
|
|
||||||
|
.workflow-text {
|
||||||
|
margin-left: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
i {
|
||||||
|
background: var(--secondary);
|
||||||
|
color: var(--dark-grey);
|
||||||
|
padding: 10px;
|
||||||
|
}
|
||||||
|
|
||||||
|
h4 {
|
||||||
|
font-size: 14px;
|
||||||
|
font-weight: 500;
|
||||||
|
margin-bottom: 5px;
|
||||||
|
}
|
||||||
|
|
||||||
|
p {
|
||||||
|
font-size: 12px;
|
||||||
|
color: var(--dark-grey);
|
||||||
|
margin: 0;
|
||||||
|
}
|
||||||
|
</style>
|
|
@ -16,7 +16,6 @@
|
||||||
name,
|
name,
|
||||||
instanceId,
|
instanceId,
|
||||||
})
|
})
|
||||||
flowy.deleteBlocks();
|
|
||||||
onClosed()
|
onClosed()
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
|
@ -23,17 +23,16 @@
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<section>
|
<section>
|
||||||
<header>
|
<button class="new-workflow-button hoverable" on:click={newWorkflow}>
|
||||||
Workflows
|
Create New Workflow
|
||||||
<i on:click={newWorkflow} class="ri-add-circle-fill" />
|
</button>
|
||||||
</header>
|
|
||||||
<ul>
|
<ul>
|
||||||
{#each $workflowStore.workflows as workflow}
|
{#each $workflowStore.workflows as workflow}
|
||||||
<li
|
<li
|
||||||
class="workflow-item"
|
class="workflow-item"
|
||||||
class:selected={workflow._id === $workflowStore.selectedWorkflowId}
|
class:selected={workflow._id === $workflowStore.selectedWorkflowId}
|
||||||
on:click={() => workflowStore.actions.select(workflow)}>
|
on:click={() => workflowStore.actions.select(workflow)}>
|
||||||
<i class="ri-stackshare-line" />
|
<i class="ri-stackshare-line" class:live={workflow.live} />
|
||||||
{workflow.name}
|
{workflow.name}
|
||||||
</li>
|
</li>
|
||||||
{/each}
|
{/each}
|
||||||
|
@ -41,16 +40,8 @@
|
||||||
</section>
|
</section>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
header {
|
|
||||||
font-size: 20px;
|
|
||||||
font-weight: bold;
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
justify-content: space-between;
|
|
||||||
}
|
|
||||||
|
|
||||||
i {
|
i {
|
||||||
color: var(--dark-grey);
|
color: #adaec4;
|
||||||
}
|
}
|
||||||
|
|
||||||
i:hover {
|
i:hover {
|
||||||
|
@ -62,6 +53,10 @@
|
||||||
padding: 0;
|
padding: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.live {
|
||||||
|
color: var(--primary);
|
||||||
|
}
|
||||||
|
|
||||||
li {
|
li {
|
||||||
font-size: 14px;
|
font-size: 14px;
|
||||||
}
|
}
|
||||||
|
@ -72,6 +67,7 @@
|
||||||
align-items: center;
|
align-items: center;
|
||||||
border-radius: 3px;
|
border-radius: 3px;
|
||||||
height: 40px;
|
height: 40px;
|
||||||
|
font-weight: 500;
|
||||||
}
|
}
|
||||||
|
|
||||||
.workflow-item i {
|
.workflow-item i {
|
||||||
|
@ -87,4 +83,15 @@
|
||||||
.workflow-item.selected {
|
.workflow-item.selected {
|
||||||
background: var(--secondary);
|
background: var(--secondary);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.new-workflow-button {
|
||||||
|
font-family: Roboto;
|
||||||
|
width: 100%;
|
||||||
|
border: solid 1px #f2f2f2;
|
||||||
|
border-radius: 2px;
|
||||||
|
background: var(--white);
|
||||||
|
height: 32px;
|
||||||
|
font-size: 12px;
|
||||||
|
font-weight: 500;
|
||||||
|
}
|
||||||
</style>
|
</style>
|
|
@ -0,0 +1,61 @@
|
||||||
|
<script>
|
||||||
|
import { onMount } from "svelte"
|
||||||
|
import { backendUiStore, workflowStore } from "builderStore"
|
||||||
|
import { WorkflowList, BlockList } from "./"
|
||||||
|
import api from "builderStore/api"
|
||||||
|
import blockDefinitions from "./blockDefinitions"
|
||||||
|
|
||||||
|
const WORKFLOW_TABS = [
|
||||||
|
{
|
||||||
|
name: "Workflows",
|
||||||
|
key: "WORKFLOWS",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "Add",
|
||||||
|
key: "ADD",
|
||||||
|
},
|
||||||
|
]
|
||||||
|
|
||||||
|
let selectedTab = "WORKFLOWS"
|
||||||
|
let definitions = []
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<section>
|
||||||
|
<header>
|
||||||
|
<span
|
||||||
|
class="hoverable"
|
||||||
|
class:selected={selectedTab === 'WORKFLOWS'}
|
||||||
|
on:click={() => (selectedTab = 'WORKFLOWS')}>
|
||||||
|
Workflows
|
||||||
|
</span>
|
||||||
|
{#if $workflowStore.selectedWorkflowId}
|
||||||
|
<span
|
||||||
|
class="hoverable"
|
||||||
|
class:selected={selectedTab === 'ADD'}
|
||||||
|
on:click={() => (selectedTab = 'ADD')}>
|
||||||
|
Add
|
||||||
|
</span>
|
||||||
|
{/if}
|
||||||
|
</header>
|
||||||
|
{#if selectedTab === 'WORKFLOWS'}
|
||||||
|
<WorkflowList />
|
||||||
|
{:else if selectedTab === 'ADD'}
|
||||||
|
<BlockList />
|
||||||
|
{/if}
|
||||||
|
</section>
|
||||||
|
|
||||||
|
<style>
|
||||||
|
header {
|
||||||
|
font-size: 20px;
|
||||||
|
font-weight: bold;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: space-between;
|
||||||
|
margin-bottom: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
span:not(.selected) {
|
||||||
|
color: var(--dark-grey);
|
||||||
|
}
|
||||||
|
|
||||||
|
</style>
|
|
@ -1,6 +1,6 @@
|
||||||
const ACTIONS = {
|
const ACTIONS = {
|
||||||
SET_STATE: {
|
SET_STATE: {
|
||||||
name: "Update UI",
|
name: "Update UI State",
|
||||||
icon: "",
|
icon: "",
|
||||||
description: "Update your User Interface with some data.",
|
description: "Update your User Interface with some data.",
|
||||||
type: "CLIENT",
|
type: "CLIENT",
|
||||||
|
@ -22,6 +22,24 @@ const ACTIONS = {
|
||||||
icon: "ri-delete-bin-line",
|
icon: "ri-delete-bin-line",
|
||||||
name: "Delete Record",
|
name: "Delete Record",
|
||||||
type: "SERVER",
|
type: "SERVER",
|
||||||
|
},
|
||||||
|
FIND_RECORD: {
|
||||||
|
description: "Delete a record from your database.",
|
||||||
|
icon: "ri-delete-bin-line",
|
||||||
|
name: "Find Record",
|
||||||
|
type: "SERVER",
|
||||||
|
},
|
||||||
|
CREATE_USER: {
|
||||||
|
description: "Create a new user.",
|
||||||
|
icon: "ri-user-add-fill",
|
||||||
|
name: "Create User",
|
||||||
|
type: "SERVER",
|
||||||
|
},
|
||||||
|
SEND_EMAIL: {
|
||||||
|
description: "Send an email.",
|
||||||
|
icon: "ri-mail-open-fill",
|
||||||
|
name: "Send Email",
|
||||||
|
type: "SERVER",
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -49,11 +67,17 @@ const TRIGGERS = {
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
const UTILITIES = {
|
const LOGIC = {
|
||||||
IFELSE: {
|
FILTER: {
|
||||||
name: "If/Else",
|
name: "Filter",
|
||||||
icon: "ri-git-branch-line",
|
icon: "ri-git-branch-line",
|
||||||
description: "Perform different actions based on a condition",
|
description: "Filter any workflows which do not meet certain conditions.",
|
||||||
|
type: "CLIENT"
|
||||||
|
},
|
||||||
|
DELAY: {
|
||||||
|
name: "Delay",
|
||||||
|
icon: "ri-git-branch-line",
|
||||||
|
description: "Delay the workflow until an amount of time has passed.",
|
||||||
type: "CLIENT"
|
type: "CLIENT"
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
@ -61,5 +85,5 @@ const UTILITIES = {
|
||||||
export default {
|
export default {
|
||||||
ACTIONS,
|
ACTIONS,
|
||||||
TRIGGERS,
|
TRIGGERS,
|
||||||
UTILITIES
|
LOGIC
|
||||||
}
|
}
|
|
@ -0,0 +1,3 @@
|
||||||
|
export { default as WorkflowPanel } from "./WorkflowPanel.svelte";
|
||||||
|
export { default as BlockList } from "./BlockList/BlockList.svelte";
|
||||||
|
export { default as WorkflowList } from "./WorkflowList/WorkflowList.svelte";
|
|
@ -1,20 +1,18 @@
|
||||||
<script>
|
<script>
|
||||||
import { workflowStore } from "builderStore"
|
import { workflowStore } from "builderStore"
|
||||||
import { WorkflowList } from "./WorkflowList"
|
import { WorkflowPanel } from "./WorkflowPanel"
|
||||||
import { BlockPanel } from "./BlockPanel"
|
import { SetupPanel } from "./SetupPanel"
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div class="root">
|
<div class="root">
|
||||||
<div class="nav">
|
<div class="nav">
|
||||||
<WorkflowList />
|
<WorkflowPanel />
|
||||||
</div>
|
</div>
|
||||||
<div class="content">
|
<div class="content">
|
||||||
<slot />
|
<slot />
|
||||||
</div>
|
</div>
|
||||||
<div class="nav">
|
<div class="nav">
|
||||||
{#if $workflowStore.selectedWorkflowId}
|
<SetupPanel />
|
||||||
<BlockPanel />
|
|
||||||
{/if}
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|
|
@ -1,49 +0,0 @@
|
||||||
<script>
|
|
||||||
import { onMount } from "svelte"
|
|
||||||
import { workflowStore, backendUiStore } from "builderStore";
|
|
||||||
import api from "builderStore/api";
|
|
||||||
|
|
||||||
let canvas
|
|
||||||
let workflow
|
|
||||||
let instanceId = $backendUiStore.selectedDatabase._id;
|
|
||||||
|
|
||||||
$: workflow = $workflowStore.workflows.find(wf => wf._id === $workflowStore.selectedWorkflowId)
|
|
||||||
|
|
||||||
// $: if (workflow && workflow.uiTree) flowy.import(workflow.uiTree);
|
|
||||||
|
|
||||||
onMount(() => {
|
|
||||||
flowy(canvas, onGrab, onRelease, onSnap);
|
|
||||||
});
|
|
||||||
|
|
||||||
function onGrab(block) {
|
|
||||||
console.log(block);
|
|
||||||
}
|
|
||||||
|
|
||||||
function onSnap(block, first, parent){
|
|
||||||
workflow.uiTree = flowy.output();
|
|
||||||
workflowStore.actions.update({ instanceId, workflow })
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
function onRelease() {
|
|
||||||
}
|
|
||||||
|
|
||||||
// function onGrab(block) {
|
|
||||||
// // When the user grabs a block
|
|
||||||
// }
|
|
||||||
// function onRelease() {
|
|
||||||
// // When the user releases a block
|
|
||||||
// console.log(flowy.output())
|
|
||||||
// }
|
|
||||||
// function onSnap(block, first, parent) {
|
|
||||||
// console.log(flowy.output())
|
|
||||||
// console.log(block, first, parent)
|
|
||||||
// // When a block snaps with another one
|
|
||||||
// }
|
|
||||||
// function onRearrange(block, parent) {
|
|
||||||
// console.log(block, parent)
|
|
||||||
// // When a block is rearranged
|
|
||||||
// }
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<section bind:this={canvas} class="canvas" />
|
|
|
@ -1,5 +1,5 @@
|
||||||
<script>
|
<script>
|
||||||
import WorkflowBuilder from "./flowy/WorkflowBuilder.svelte";
|
import WorkflowBuilder from "./WorkflowBuilder/WorkflowBuilder.svelte";
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<WorkflowBuilder />
|
<WorkflowBuilder />
|
|
@ -1,38 +0,0 @@
|
||||||
import api from "builderStore/api";
|
|
||||||
|
|
||||||
class Orchestrator {
|
|
||||||
set strategy(strategy) {
|
|
||||||
this._stategy = strategy
|
|
||||||
}
|
|
||||||
|
|
||||||
execute(workflow) {
|
|
||||||
this._strategy.execute(workflow);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const ClientStrategy = {
|
|
||||||
execute: function(workflow) {
|
|
||||||
const block = workflow.next;
|
|
||||||
const EXECUTE_WORKFLOW_URL = `api/${workflow.instanceId}/workflows/${workflow._id}`;
|
|
||||||
|
|
||||||
switch (block.type) {
|
|
||||||
case "CLIENT":
|
|
||||||
// fetch the workflow code from the server, then execute it here in the client
|
|
||||||
// catch any errors
|
|
||||||
// check against the conditions in the workflow
|
|
||||||
// if everything is fine, recurse
|
|
||||||
this.execute(workflow.next);
|
|
||||||
break;
|
|
||||||
case "SERVER":
|
|
||||||
// hit the server endpoint and wait for the response
|
|
||||||
// catch any errors
|
|
||||||
// check against the conditions in the workflow
|
|
||||||
// if everything is fine, recurse
|
|
||||||
await api.post()
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -2,7 +2,21 @@
|
||||||
import { store } from "builderStore"
|
import { store } from "builderStore"
|
||||||
import AppList from "components/start/AppList.svelte"
|
import AppList from "components/start/AppList.svelte"
|
||||||
import { onMount } from "svelte"
|
import { onMount } from "svelte"
|
||||||
|
import ActionButton from "components/common/ActionButton.svelte"
|
||||||
import IconButton from "components/common/IconButton.svelte"
|
import IconButton from "components/common/IconButton.svelte"
|
||||||
|
import {
|
||||||
|
SettingsIcon,
|
||||||
|
AppsIcon,
|
||||||
|
UpdatesIcon,
|
||||||
|
HostingIcon,
|
||||||
|
DocumentationIcon,
|
||||||
|
TutorialsIcon,
|
||||||
|
CommunityIcon,
|
||||||
|
ContributionIcon,
|
||||||
|
BugIcon,
|
||||||
|
EmailIcon,
|
||||||
|
TwitterIcon,
|
||||||
|
} from "components/common/Icons/"
|
||||||
import Spinner from "components/common/Spinner.svelte"
|
import Spinner from "components/common/Spinner.svelte"
|
||||||
|
|
||||||
let promise = getApps()
|
let promise = getApps()
|
||||||
|
@ -19,7 +33,116 @@
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<main>
|
<div class="root">
|
||||||
|
<div class="ui-nav">
|
||||||
|
<div class="home-logo">
|
||||||
|
<img src="/_builder/assets/bb-logo.svg" alt="Budibase icon" />
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="nav-section">
|
||||||
|
<div class="nav-section-title">Build</div>
|
||||||
|
<div class="nav-item-home">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<AppsIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Apps</div>
|
||||||
|
</div>
|
||||||
|
<div class="nav-item">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<SettingsIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Settings</div>
|
||||||
|
</div>
|
||||||
|
<a href="https://budibase.con/login" target="_blank" class="nav-item">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<UpdatesIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Updates</div>
|
||||||
|
</a>
|
||||||
|
<a href="https://budibase.con/login" target="_blank" class="nav-item">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<HostingIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Hosting</div>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="nav-section">
|
||||||
|
<div class="nav-section-title">Learn</div>
|
||||||
|
<a href="https://docs.budibase.com/" target="_blank" class="nav-item">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<DocumentationIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Documentation</div>
|
||||||
|
</a>
|
||||||
|
<a
|
||||||
|
href="https://docs.budibase.com/tutorial/quick-start"
|
||||||
|
target="_blank"
|
||||||
|
class="nav-item">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<TutorialsIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Tutorials</div>
|
||||||
|
</a>
|
||||||
|
<a href="https://forum.budibase.com/" target="_blank" class="nav-item">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<CommunityIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Community</div>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="nav-section">
|
||||||
|
<div class="nav-section-title">Contact</div>
|
||||||
|
<a
|
||||||
|
href="https://github.com/Budibase/budibase/blob/master/CONTRIBUTING.md"
|
||||||
|
target="_blank"
|
||||||
|
class="nav-item">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<ContributionIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Contribute to our product</div>
|
||||||
|
</a>
|
||||||
|
<a
|
||||||
|
href="https://github.com/Budibase/budibase/issues"
|
||||||
|
target="_blank"
|
||||||
|
class="nav-item">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<BugIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Report bug</div>
|
||||||
|
</a>
|
||||||
|
<a href="mailto:support@budibase.com" target="_blank" class="nav-item">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<EmailIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Email</div>
|
||||||
|
</a>
|
||||||
|
<a href="https://twitter.com/budibase" target="_blank" class="nav-item">
|
||||||
|
<span class="nav-item-icon">
|
||||||
|
<TwitterIcon />
|
||||||
|
</span>
|
||||||
|
<div class="nav-item-title">Twitter</div>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="main">
|
||||||
|
<div class="welcome">Welcome to Budibase</div>
|
||||||
|
<div class="banner">
|
||||||
|
<div class="banner-content">
|
||||||
|
<div class="banner-header">
|
||||||
|
Every accomplishment starts with a decision to try.
|
||||||
|
</div>
|
||||||
|
<button class="banner-button" type="button">
|
||||||
|
<i class="ri-add-circle-fill" />
|
||||||
|
Create New Web App
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
<div class="banner-image">
|
||||||
|
<img src="/_builder/assets/banner-image.png" alt="Bannerimage" />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
{#await promise}
|
{#await promise}
|
||||||
<div class="spinner-container">
|
<div class="spinner-container">
|
||||||
<Spinner />
|
<Spinner />
|
||||||
|
@ -29,13 +152,156 @@
|
||||||
{:catch err}
|
{:catch err}
|
||||||
<h1 style="color:red">{err}</h1>
|
<h1 style="color:red">{err}</h1>
|
||||||
{/await}
|
{/await}
|
||||||
</main>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
main {
|
.root {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 275px 1fr;
|
||||||
height: 100%;
|
height: 100%;
|
||||||
width: 100%;
|
width: 100%;
|
||||||
font-family: "Roboto", Helvetica, Arial, sans-serif;
|
background: var(--grey-light);
|
||||||
|
}
|
||||||
|
|
||||||
|
@media only screen and (min-width: 1800px) {
|
||||||
|
.root {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 300px 1fr;
|
||||||
|
height: 100%;
|
||||||
|
width: 100%;
|
||||||
|
background: var(--grey-light);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.main {
|
||||||
|
grid-column: 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
.ui-nav {
|
||||||
|
grid-column: 1;
|
||||||
|
background-color: var(--white);
|
||||||
|
padding: 20px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
border-right: 1px solid var(--grey-dark);
|
||||||
|
}
|
||||||
|
|
||||||
|
.home-logo {
|
||||||
|
cursor: pointer;
|
||||||
|
height: 40px;
|
||||||
|
margin-bottom: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.home-logo img {
|
||||||
|
height: 40px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-section {
|
||||||
|
margin: 20px 0px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-section-title {
|
||||||
|
font-size: 20px;
|
||||||
|
color: var(--ink);
|
||||||
|
font-weight: 700;
|
||||||
|
margin-bottom: 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-item {
|
||||||
|
cursor: pointer;
|
||||||
|
margin: 0px 0px 4px 0px;
|
||||||
|
padding: 0px 0px 0px 12px;
|
||||||
|
height: 40px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: row;
|
||||||
|
align-items: center;
|
||||||
|
box-sizing: border-box;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-item-home {
|
||||||
|
cursor: pointer;
|
||||||
|
margin: 0px 0px 4px 0px;
|
||||||
|
padding: 0px 0px 0px 12px;
|
||||||
|
height: 40px;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: row;
|
||||||
|
align-items: center;
|
||||||
|
box-sizing: border-box;
|
||||||
|
background-color: var(--blue-light);
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-item:hover {
|
||||||
|
background-color: var(--grey-light);
|
||||||
|
border-radius: 3px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-item::selection {
|
||||||
|
background-color: var(--blue-light);
|
||||||
|
border-radius: 3px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-item-title {
|
||||||
|
font-size: 14px;
|
||||||
|
color: var(--ink);
|
||||||
|
font-weight: 500;
|
||||||
|
margin-left: 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.nav-item-icon {
|
||||||
|
color: var(--ink-light);
|
||||||
|
}
|
||||||
|
|
||||||
|
.welcome {
|
||||||
|
margin: 60px 80px 0px 80px;
|
||||||
|
font-size: 42px;
|
||||||
|
color: var(--ink);
|
||||||
|
font-weight: 900;
|
||||||
|
}
|
||||||
|
|
||||||
|
.banner {
|
||||||
|
display: grid;
|
||||||
|
grid-template-columns: 1fr 1fr;
|
||||||
|
margin: 20px 80px 40px 80px;
|
||||||
|
background-image: linear-gradient(-45deg, #7f9ceb, #1d2f77);
|
||||||
|
border-radius: 10px;
|
||||||
|
max-height: 280px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.banner-content {
|
||||||
|
padding: 60px;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media only screen and (min-width: 1800px) {
|
||||||
|
.banner-content {
|
||||||
|
padding: 80px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.banner-header {
|
||||||
|
font-size: 24px;
|
||||||
|
color: var(--white);
|
||||||
|
font-weight: 500;
|
||||||
|
margin-bottom: 20px;
|
||||||
|
}
|
||||||
|
|
||||||
|
@media only screen and (min-width: 1800px) {
|
||||||
|
.banner-header {
|
||||||
|
font-size: 36px;
|
||||||
|
color: var(--white);
|
||||||
|
font-weight: 500;
|
||||||
|
margin-bottom: 20px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.banner-image {
|
||||||
|
z-index: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
.banner-image img {
|
||||||
|
max-height: 400px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.spinner-container {
|
.spinner-container {
|
||||||
|
@ -45,4 +311,28 @@
|
||||||
align-items: center;
|
align-items: center;
|
||||||
justify-content: center;
|
justify-content: center;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.banner-button {
|
||||||
|
background-color: var(--white);
|
||||||
|
color: var(--ink);
|
||||||
|
padding: 12px 20px;
|
||||||
|
border-radius: 5px;
|
||||||
|
border: 0px transparent solid;
|
||||||
|
font-size: 16px;
|
||||||
|
font-weight: 400;
|
||||||
|
cursor: pointer;
|
||||||
|
transition: all 0.2s;
|
||||||
|
box-sizing: border-box;
|
||||||
|
align-items: center;
|
||||||
|
display: flex;
|
||||||
|
}
|
||||||
|
|
||||||
|
.ri-add-circle-fill {
|
||||||
|
margin-right: 4px;
|
||||||
|
font-size: 24px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.banner-button:hover {
|
||||||
|
background-color: var(--grey);
|
||||||
|
}
|
||||||
</style>
|
</style>
|
||||||
|
|
|
@ -1,320 +1,55 @@
|
||||||
import {
|
import {
|
||||||
generate_css,
|
generate_css,
|
||||||
make_margin,
|
|
||||||
generate_screen_css,
|
generate_screen_css,
|
||||||
|
generate_array_styles
|
||||||
} from "../src/builderStore/generate_css.js"
|
} from "../src/builderStore/generate_css.js"
|
||||||
|
|
||||||
describe("make_margin", () => {
|
|
||||||
test("it should generate a valid rule", () => {
|
|
||||||
expect(make_margin(["1", "1", "1", "1"])).toEqual("1px 1px 1px 1px")
|
|
||||||
})
|
|
||||||
|
|
||||||
test("empty values should output 0", () => {
|
|
||||||
expect(make_margin(["1", "1", "", ""])).toEqual("1px 1px 0px 0px")
|
|
||||||
expect(make_margin(["1", "", "", "1"])).toEqual("1px 0px 0px 1px")
|
|
||||||
expect(make_margin(["", "", "", ""])).toEqual("0px 0px 0px 0px")
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
describe("generate_css", () => {
|
describe("generate_css", () => {
|
||||||
test("it should generate a valid css rule: grid-area", () => {
|
|
||||||
expect(generate_css({ layout: { gridarea: ["", "", "", ""] } })).toEqual({
|
test("Check how partially empty arrays are handled", () => {
|
||||||
layout: "",
|
expect(["", "5", "", ""].map(generate_array_styles)).toEqual(["0px", "5px", "0px", "0px"])
|
||||||
position: "",
|
|
||||||
})
|
|
||||||
})
|
})
|
||||||
|
|
||||||
test("it should generate a valid css rule: grid-gap", () => {
|
test("Check how array styles are output", () => {
|
||||||
expect(generate_css({ layout: { gap: "10" } })).toEqual({
|
expect(generate_css({ margin: ["0", "10", "0", "15"] })).toBe("margin: 0px 10px 0px 15px;")
|
||||||
layout: "grid-gap: 10px;\ndisplay: grid;",
|
|
||||||
position: "",
|
|
||||||
})
|
|
||||||
})
|
})
|
||||||
|
|
||||||
test("it should generate a valid css rule: column 1", () => {
|
test("Check handling of an array with empty string values", () => {
|
||||||
expect(generate_css({ position: { column: ["", ""] } })).toEqual({
|
expect(generate_css({ padding: ["", "", "", ""] })).toBe("")
|
||||||
layout: "",
|
|
||||||
position: "",
|
|
||||||
})
|
|
||||||
})
|
})
|
||||||
|
|
||||||
test("it should generate a valid css rule: column 2", () => {
|
test("Check handling of an empty array", () => {
|
||||||
expect(generate_css({ position: { column: ["1", ""] } })).toEqual({
|
expect(generate_css({ margin: [] })).toBe("")
|
||||||
position: "grid-column-start: 1;",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
})
|
||||||
|
|
||||||
test("it should generate a valid css rule: column 3", () => {
|
test("Check handling of valid font property", () => {
|
||||||
expect(generate_css({ position: { column: ["", "1"] } })).toEqual({
|
expect(generate_css({ "font-size": "10px" })).toBe("font-size: 10px;")
|
||||||
position: "grid-column-end: 1;",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: column 4", () => {
|
|
||||||
expect(generate_css({ position: { column: ["1", "1"] } })).toEqual({
|
|
||||||
position: "grid-column-start: 1;\ngrid-column-end: 1;",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: row 1", () => {
|
|
||||||
expect(generate_css({ position: { row: ["", ""] } })).toEqual({
|
|
||||||
layout: "",
|
|
||||||
position: "",
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: row 2", () => {
|
|
||||||
expect(generate_css({ position: { row: ["1", ""] } })).toEqual({
|
|
||||||
position: "grid-row-start: 1;",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: row 3", () => {
|
|
||||||
expect(generate_css({ position: { row: ["", "1"] } })).toEqual({
|
|
||||||
position: "grid-row-end: 1;",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: row 4", () => {
|
|
||||||
expect(generate_css({ position: { row: ["1", "1"] } })).toEqual({
|
|
||||||
position: "grid-row-start: 1;\ngrid-row-end: 1;",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: padding 1", () => {
|
|
||||||
expect(
|
|
||||||
generate_css({ position: { padding: ["1", "1", "1", "1"] } })
|
|
||||||
).toEqual({
|
|
||||||
position: "padding: 1px 1px 1px 1px;",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: padding 2", () => {
|
|
||||||
expect(generate_css({ position: { padding: ["1", "", "", "1"] } })).toEqual(
|
|
||||||
{
|
|
||||||
position: "padding: 1px 0px 0px 1px;",
|
|
||||||
layout: "",
|
|
||||||
}
|
|
||||||
)
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: margin 1", () => {
|
|
||||||
expect(
|
|
||||||
generate_css({ position: { margin: ["1", "1", "1", "1"] } })
|
|
||||||
).toEqual({
|
|
||||||
position: "margin: 1px 1px 1px 1px;",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: margin 2", () => {
|
|
||||||
expect(generate_css({ position: { margin: ["1", "", "", "1"] } })).toEqual({
|
|
||||||
position: "margin: 1px 0px 0px 1px;",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: z-index 1", () => {
|
|
||||||
expect(generate_css({ position: { zindex: "" } })).toEqual({
|
|
||||||
position: "",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
|
||||||
|
|
||||||
test("it should generate a valid css rule: z-index 2", () => {
|
|
||||||
expect(generate_css({ position: { zindex: "1" } })).toEqual({
|
|
||||||
position: "z-index: 1;",
|
|
||||||
layout: "",
|
|
||||||
})
|
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|
||||||
describe("generate_screen_css", () => {
|
describe("generate_screen_css", () => {
|
||||||
test("it should compile the css for a list of components", () => {
|
const normalComponent = { _id: "123-456", _component: "@standard-components/header", _children: [], _styles: { normal: { "font-size": "16px" }, hover: {}, active: {}, selected: {} } }
|
||||||
const components = [
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 1,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 2,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 3,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 4,
|
|
||||||
},
|
|
||||||
]
|
|
||||||
|
|
||||||
const compiled = `.pos-1 {
|
test("Test generation of normal css styles", () => {
|
||||||
margin: 1px 1px 1px 1px;
|
expect(generate_screen_css([normalComponent])).toBe(".header-123-456 {\nfont-size: 16px;\n}")
|
||||||
}
|
|
||||||
.lay-1 {
|
|
||||||
|
|
||||||
}
|
|
||||||
.pos-2 {
|
|
||||||
margin: 1px 1px 1px 1px;
|
|
||||||
}
|
|
||||||
.lay-2 {
|
|
||||||
|
|
||||||
}
|
|
||||||
.pos-3 {
|
|
||||||
margin: 1px 1px 1px 1px;
|
|
||||||
}
|
|
||||||
.lay-3 {
|
|
||||||
|
|
||||||
}
|
|
||||||
.pos-4 {
|
|
||||||
margin: 1px 1px 1px 1px;
|
|
||||||
}
|
|
||||||
.lay-4 {
|
|
||||||
|
|
||||||
}`
|
|
||||||
|
|
||||||
expect(generate_screen_css(components)).toEqual(compiled)
|
|
||||||
})
|
})
|
||||||
|
|
||||||
test("it should compile the css for a list of components", () => {
|
const hoverComponent = { _id: "123-456", _component: "@standard-components/header", _children: [], _styles: { normal: {}, hover: {"font-size": "16px"}, active: {}, selected: {} } }
|
||||||
const components = [
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 1,
|
|
||||||
_children: [
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 2,
|
|
||||||
_children: [
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 3,
|
|
||||||
_children: [
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 4,
|
|
||||||
_children: [
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 5,
|
|
||||||
_children: [],
|
|
||||||
},
|
|
||||||
],
|
|
||||||
},
|
|
||||||
],
|
|
||||||
},
|
|
||||||
],
|
|
||||||
},
|
|
||||||
],
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 6,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 7,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
_styles: {
|
|
||||||
layout: { gridarea: ["", "", "", ""] },
|
|
||||||
position: { margin: ["1", "1", "1", "1"] },
|
|
||||||
},
|
|
||||||
_id: 8,
|
|
||||||
},
|
|
||||||
]
|
|
||||||
|
|
||||||
const compiled = `.pos-1 {
|
test("Test generation of hover css styles", () => {
|
||||||
margin: 1px 1px 1px 1px;
|
expect(generate_screen_css([hoverComponent])).toBe(".header-123-456:hover {\nfont-size: 16px;\n}")
|
||||||
}
|
})
|
||||||
.lay-1 {
|
|
||||||
|
|
||||||
}
|
const selectedComponent = { _id: "123-456", _component: "@standard-components/header", _children: [], _styles: { normal: {}, hover: {}, active: {}, selected: { "font-size": "16px" } } }
|
||||||
.pos-2 {
|
|
||||||
margin: 1px 1px 1px 1px;
|
|
||||||
}
|
|
||||||
.lay-2 {
|
|
||||||
|
|
||||||
}
|
test("Test generation of selection css styles", () => {
|
||||||
.pos-3 {
|
expect(generate_screen_css([selectedComponent])).toBe(".header-123-456::selection {\nfont-size: 16px;\n}")
|
||||||
margin: 1px 1px 1px 1px;
|
})
|
||||||
}
|
|
||||||
.lay-3 {
|
|
||||||
|
|
||||||
}
|
const emptyComponent = { _id: "123-456", _component: "@standard-components/header", _children: [], _styles: { normal: {}, hover: {}, active: {}, selected: {} } }
|
||||||
.pos-4 {
|
|
||||||
margin: 1px 1px 1px 1px;
|
|
||||||
}
|
|
||||||
.lay-4 {
|
|
||||||
|
|
||||||
}
|
test.only("Testing handling of empty component styles", () => {
|
||||||
.pos-5 {
|
expect(generate_screen_css([emptyComponent])).toBe("")
|
||||||
margin: 1px 1px 1px 1px;
|
|
||||||
}
|
|
||||||
.lay-5 {
|
|
||||||
|
|
||||||
}
|
|
||||||
.pos-6 {
|
|
||||||
margin: 1px 1px 1px 1px;
|
|
||||||
}
|
|
||||||
.lay-6 {
|
|
||||||
|
|
||||||
}
|
|
||||||
.pos-7 {
|
|
||||||
margin: 1px 1px 1px 1px;
|
|
||||||
}
|
|
||||||
.lay-7 {
|
|
||||||
|
|
||||||
}
|
|
||||||
.pos-8 {
|
|
||||||
margin: 1px 1px 1px 1px;
|
|
||||||
}
|
|
||||||
.lay-8 {
|
|
||||||
|
|
||||||
}`
|
|
||||||
|
|
||||||
expect(generate_screen_css(components)).toEqual(compiled)
|
|
||||||
})
|
})
|
||||||
})
|
})
|
|
@ -9,8 +9,10 @@
|
||||||
"_id": 0,
|
"_id": 0,
|
||||||
"type": "div",
|
"type": "div",
|
||||||
"_styles": {
|
"_styles": {
|
||||||
"layout": {},
|
"normal": {},
|
||||||
"position": {}
|
"hover": {},
|
||||||
|
"active": {},
|
||||||
|
"selected": {}
|
||||||
},
|
},
|
||||||
"_code": ""
|
"_code": ""
|
||||||
},
|
},
|
||||||
|
|
|
@ -9,8 +9,10 @@
|
||||||
"_id": 1,
|
"_id": 1,
|
||||||
"type": "div",
|
"type": "div",
|
||||||
"_styles": {
|
"_styles": {
|
||||||
"layout": {},
|
"normal": {},
|
||||||
"position": {}
|
"hover": {},
|
||||||
|
"active": {},
|
||||||
|
"selected": {}
|
||||||
},
|
},
|
||||||
"_code": ""
|
"_code": ""
|
||||||
},
|
},
|
||||||
|
|
|
@ -9,8 +9,10 @@
|
||||||
"_id": 0,
|
"_id": 0,
|
||||||
"type": "div",
|
"type": "div",
|
||||||
"_styles": {
|
"_styles": {
|
||||||
"layout": {},
|
"normal": {},
|
||||||
"position": {}
|
"hover": {},
|
||||||
|
"active": {},
|
||||||
|
"selected": {}
|
||||||
},
|
},
|
||||||
"_code": ""
|
"_code": ""
|
||||||
},
|
},
|
||||||
|
|
|
@ -2,7 +2,6 @@ import Orchestrator, { clientStrategy } from "./orchestrator";
|
||||||
|
|
||||||
|
|
||||||
export const triggerWorkflow = api => ({ workflow }) => {
|
export const triggerWorkflow = api => ({ workflow }) => {
|
||||||
console.log(workflow);
|
|
||||||
const workflowOrchestrator = new Orchestrator(
|
const workflowOrchestrator = new Orchestrator(
|
||||||
api,
|
api,
|
||||||
"inst_60dd510_700f7dc06735403e81d5af91072d7241"
|
"inst_60dd510_700f7dc06735403e81d5af91072d7241"
|
||||||
|
|
|
@ -31,7 +31,7 @@ export default class Orchestrator {
|
||||||
// Execute a workflow from a running budibase app
|
// Execute a workflow from a running budibase app
|
||||||
export const clientStrategy = {
|
export const clientStrategy = {
|
||||||
context: {},
|
context: {},
|
||||||
bindContextArgs: function(args) {
|
bindContextArgs: function(args, api) {
|
||||||
const mappedArgs = { ...args };
|
const mappedArgs = { ...args };
|
||||||
|
|
||||||
console.log("original args", args)
|
console.log("original args", args)
|
||||||
|
@ -50,12 +50,16 @@ export const clientStrategy = {
|
||||||
|
|
||||||
// if the value is bound to state
|
// if the value is bound to state
|
||||||
if (argValue.startsWith("$state")) {
|
if (argValue.startsWith("$state")) {
|
||||||
const path = argValue.match("$context.", "");
|
const path = argValue.replace("$state.", "");
|
||||||
// pass in the value from context
|
// pass in the value from state
|
||||||
mappedArgs[arg] = get(path, this.context);
|
// TODO: not working
|
||||||
|
mappedArgs[arg] = api.getState(path);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
console.log(mappedArgs);
|
||||||
|
|
||||||
return Object.values(mappedArgs);
|
return Object.values(mappedArgs);
|
||||||
},
|
},
|
||||||
run: async function({ workflow, api, instanceId }) {
|
run: async function({ workflow, api, instanceId }) {
|
||||||
|
@ -85,7 +89,7 @@ export const clientStrategy = {
|
||||||
url: EXECUTE_WORKFLOW_URL,
|
url: EXECUTE_WORKFLOW_URL,
|
||||||
body: {
|
body: {
|
||||||
action: block.actionId,
|
action: block.actionId,
|
||||||
args: block.args
|
args: this.bindContextArgs(block.args, api)
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -31,7 +31,7 @@ export const attachChildren = initialiseOpts => (htmlElement, options) => {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
htmlElement.classList.add(`lay-${treeNode.props._id}`)
|
// htmlElement.classList.add(`lay-${treeNode.props._id}`)
|
||||||
|
|
||||||
const childNodes = []
|
const childNodes = []
|
||||||
for (let childProps of treeNode.props._children) {
|
for (let childProps of treeNode.props._children) {
|
||||||
|
|
|
@ -35,8 +35,9 @@ export const prepareRenderComponent = ({
|
||||||
thisNode.rootElement =
|
thisNode.rootElement =
|
||||||
htmlElement.children[htmlElement.children.length - 1]
|
htmlElement.children[htmlElement.children.length - 1]
|
||||||
|
|
||||||
|
let [componentName] = props._component.match(/[a-z]*$/)
|
||||||
if (props._id && thisNode.rootElement) {
|
if (props._id && thisNode.rootElement) {
|
||||||
thisNode.rootElement.classList.add(`pos-${props._id}`)
|
thisNode.rootElement.classList.add(`${componentName}-${props._id}`)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
After Width: | Height: | Size: 109 KiB |
After Width: | Height: | Size: 109 KiB |
|
@ -0,0 +1,31 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<!-- Generator: Adobe Illustrator 24.1.2, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
|
||||||
|
<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
|
||||||
|
viewBox="0 0 128 128" style="enable-background:new 0 0 128 128;" xml:space="preserve">
|
||||||
|
<style type="text/css">
|
||||||
|
.st0{fill:#393C44;}
|
||||||
|
.st1{fill:#FFFFFF;}
|
||||||
|
</style>
|
||||||
|
<g>
|
||||||
|
<path class="st0" d="M117.33,128H10.67C4.78,128,0,123.22,0,117.33V10.67C0,4.78,4.78,0,10.67,0h106.67
|
||||||
|
C123.22,0,128,4.78,128,10.67v106.67C128,123.22,123.22,128,117.33,128z"/>
|
||||||
|
<g>
|
||||||
|
<path class="st1" d="M75.94,32v27.84c3.14-3.38,7.07-5.07,11.79-5.07c2.8,0,5.37,0.54,7.7,1.63c2.33,1.09,4.32,2.55,5.97,4.39
|
||||||
|
c1.65,1.84,2.93,4.01,3.87,6.51c0.93,2.5,1.4,5.16,1.4,7.98c0,2.87-0.48,5.57-1.44,8.09c-0.96,2.52-2.3,4.72-4.02,6.58
|
||||||
|
c-1.72,1.87-3.75,3.34-6.08,4.43C92.8,95.46,90.28,96,87.58,96c-4.91,0-8.79-1.84-11.64-5.52v4.31H62.6V32H75.94z M92.74,75.5
|
||||||
|
c0-1.21-0.22-2.36-0.66-3.44c-0.44-1.08-1.06-2.03-1.84-2.84c-0.79-0.81-1.7-1.45-2.73-1.93c-1.03-0.48-2.16-0.72-3.39-0.72
|
||||||
|
c-1.18,0-2.28,0.23-3.32,0.68c-1.03,0.45-1.93,1.09-2.69,1.89c-0.76,0.81-1.38,1.75-1.84,2.84c-0.47,1.09-0.7,2.23-0.7,3.44
|
||||||
|
s0.22,2.34,0.66,3.4c0.44,1.06,1.06,1.98,1.84,2.76c0.79,0.78,1.71,1.41,2.76,1.89c1.06,0.48,2.17,0.72,3.35,0.72
|
||||||
|
c1.18,0,2.28-0.23,3.32-0.68c1.03-0.45,1.93-1.08,2.69-1.89c0.76-0.81,1.37-1.74,1.84-2.8C92.51,77.77,92.74,76.66,92.74,75.5z"/>
|
||||||
|
</g>
|
||||||
|
<g>
|
||||||
|
<path class="st1" d="M34.67,32v27.84c3.14-3.38,7.07-5.07,11.79-5.07c2.8,0,5.37,0.54,7.7,1.63c2.33,1.09,4.32,2.55,5.97,4.39
|
||||||
|
c1.65,1.84,2.93,4.01,3.87,6.51c0.93,2.5,1.4,5.16,1.4,7.98c0,2.87-0.48,5.57-1.44,8.09c-0.96,2.52-2.3,4.72-4.02,6.58
|
||||||
|
c-1.72,1.87-3.75,3.34-6.08,4.43C51.53,95.46,49.01,96,46.31,96c-4.91,0-8.79-1.84-11.64-5.52v4.31H21.33V32H34.67z M51.47,75.5
|
||||||
|
c0-1.21-0.22-2.36-0.66-3.44c-0.44-1.08-1.06-2.03-1.84-2.84c-0.79-0.81-1.7-1.45-2.73-1.93c-1.03-0.48-2.16-0.72-3.39-0.72
|
||||||
|
c-1.18,0-2.28,0.23-3.32,0.68c-1.03,0.45-1.93,1.09-2.69,1.89c-0.76,0.81-1.38,1.75-1.84,2.84c-0.47,1.09-0.7,2.23-0.7,3.44
|
||||||
|
s0.22,2.34,0.66,3.4c0.44,1.06,1.06,1.98,1.84,2.76c0.79,0.78,1.71,1.41,2.76,1.89c1.06,0.48,2.17,0.72,3.35,0.72
|
||||||
|
c1.18,0,2.28-0.23,3.32-0.68c1.03-0.45,1.93-1.08,2.69-1.89c0.76-0.81,1.37-1.74,1.84-2.8C51.24,77.77,51.47,76.66,51.47,75.5z"/>
|
||||||
|
</g>
|
||||||
|
</g>
|
||||||
|
</svg>
|
After Width: | Height: | Size: 2.3 KiB |
After Width: | Height: | Size: 241 KiB |
After Width: | Height: | Size: 381 KiB |
|
@ -44,6 +44,7 @@
|
||||||
"@budibase/client": "^0.0.32",
|
"@budibase/client": "^0.0.32",
|
||||||
"@budibase/core": "^0.0.32",
|
"@budibase/core": "^0.0.32",
|
||||||
"@koa/router": "^8.0.0",
|
"@koa/router": "^8.0.0",
|
||||||
|
"@sendgrid/mail": "^7.1.1",
|
||||||
"ajv": "^6.12.2",
|
"ajv": "^6.12.2",
|
||||||
"bcryptjs": "^2.4.3",
|
"bcryptjs": "^2.4.3",
|
||||||
"dotenv": "^8.2.0",
|
"dotenv": "^8.2.0",
|
||||||
|
|
|
@ -0,0 +1,27 @@
|
||||||
|
const sgMail = require('@sendgrid/mail');
|
||||||
|
|
||||||
|
sgMail.setApiKey(process.env.SENDGRID_API_KEY);
|
||||||
|
|
||||||
|
module.exports = async function sendEmail(args) {
|
||||||
|
|
||||||
|
const msg = {
|
||||||
|
to: args.to,
|
||||||
|
from: args.from,
|
||||||
|
subject: args.subject,
|
||||||
|
text: args.text
|
||||||
|
};
|
||||||
|
|
||||||
|
try {
|
||||||
|
await sgMail.send(msg);
|
||||||
|
return {
|
||||||
|
success: true,
|
||||||
|
err
|
||||||
|
}
|
||||||
|
} catch (err) {
|
||||||
|
return {
|
||||||
|
success: false,
|
||||||
|
err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -65,7 +65,7 @@ exports.update = async function(ctx) {
|
||||||
exports.fetch = async function(ctx) {
|
exports.fetch = async function(ctx) {
|
||||||
const db = new CouchDB(ctx.params.instanceId)
|
const db = new CouchDB(ctx.params.instanceId)
|
||||||
const response = await db.query(`database/by_type`, {
|
const response = await db.query(`database/by_type`, {
|
||||||
type: "workflow",
|
key: ["workflow"],
|
||||||
include_docs: true,
|
include_docs: true,
|
||||||
})
|
})
|
||||||
ctx.body = response.rows.map(row => row.doc)
|
ctx.body = response.rows.map(row => row.doc)
|
||||||
|
|
|
@ -194,6 +194,20 @@
|
||||||
lodash "^4.17.13"
|
lodash "^4.17.13"
|
||||||
to-fast-properties "^2.0.0"
|
to-fast-properties "^2.0.0"
|
||||||
|
|
||||||
|
"@budibase/client@^0.0.32":
|
||||||
|
version "0.0.32"
|
||||||
|
resolved "https://registry.yarnpkg.com/@budibase/client/-/client-0.0.32.tgz#76d9f147563a0bf939eae7f32ce75b2a527ba496"
|
||||||
|
integrity sha512-jmCCLn0CUoQbL6h623S5IqK6+GYLqX3WzUTZInSb1SCBOM3pI0eLP5HwTR6s7r42SfD0v9jTWRdyTnHiElNj8A==
|
||||||
|
dependencies:
|
||||||
|
"@nx-js/compiler-util" "^2.0.0"
|
||||||
|
bcryptjs "^2.4.3"
|
||||||
|
deep-equal "^2.0.1"
|
||||||
|
lodash "^4.17.15"
|
||||||
|
lunr "^2.3.5"
|
||||||
|
regexparam "^1.3.0"
|
||||||
|
shortid "^2.2.8"
|
||||||
|
svelte "^3.9.2"
|
||||||
|
|
||||||
"@budibase/core@^0.0.32":
|
"@budibase/core@^0.0.32":
|
||||||
version "0.0.32"
|
version "0.0.32"
|
||||||
resolved "https://registry.yarnpkg.com/@budibase/core/-/core-0.0.32.tgz#c5d9ab869c5e9596a1ac337aaf041e795b1cc7fa"
|
resolved "https://registry.yarnpkg.com/@budibase/core/-/core-0.0.32.tgz#c5d9ab869c5e9596a1ac337aaf041e795b1cc7fa"
|
||||||
|
@ -409,6 +423,30 @@
|
||||||
resolved "https://registry.yarnpkg.com/@nx-js/compiler-util/-/compiler-util-2.0.0.tgz#c74c12165fa2f017a292bb79af007e8fce0af297"
|
resolved "https://registry.yarnpkg.com/@nx-js/compiler-util/-/compiler-util-2.0.0.tgz#c74c12165fa2f017a292bb79af007e8fce0af297"
|
||||||
integrity sha512-AxSQbwj9zqt8DYPZ6LwZdytqnwfiOEdcFdq4l8sdjkZmU2clTht7RDLCI8xvkp7KqgcNaOGlTeCM55TULWruyQ==
|
integrity sha512-AxSQbwj9zqt8DYPZ6LwZdytqnwfiOEdcFdq4l8sdjkZmU2clTht7RDLCI8xvkp7KqgcNaOGlTeCM55TULWruyQ==
|
||||||
|
|
||||||
|
"@sendgrid/client@^7.1.1":
|
||||||
|
version "7.1.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/@sendgrid/client/-/client-7.1.1.tgz#09a25e58ac7e5321d66807e7110ff0fb61bb534f"
|
||||||
|
integrity sha512-V2BmOO81wHNmbTDwTJ07Olb9dWrj1G19xK4crwds68b9R0w05aOWDddZTvpn9mZnHwIJYqcZcBJuhdHDejuSHg==
|
||||||
|
dependencies:
|
||||||
|
"@sendgrid/helpers" "^7.0.1"
|
||||||
|
axios "^0.19.2"
|
||||||
|
|
||||||
|
"@sendgrid/helpers@^7.0.1":
|
||||||
|
version "7.0.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/@sendgrid/helpers/-/helpers-7.0.1.tgz#b97debc793ed3f9f56102e12c2a6d2bbbf0ffb78"
|
||||||
|
integrity sha512-i/zsissq1upgdywtuJKysaplJJZC24GdtEKiJC1IRlXvBHzIjH4eU+rqUFO8h+hGji3UMURGgMFuLUXTUYvZ9w==
|
||||||
|
dependencies:
|
||||||
|
chalk "^2.0.1"
|
||||||
|
deepmerge "^4.2.2"
|
||||||
|
|
||||||
|
"@sendgrid/mail@^7.1.1":
|
||||||
|
version "7.1.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/@sendgrid/mail/-/mail-7.1.1.tgz#26191594722d5961de1b61cd9c48fa9a69fd197b"
|
||||||
|
integrity sha512-VXdJ9J6vBNMw+wMIGFRvms6EmV6pvoRHMWoLJGweHlsZDnvmK3rWUnnNaS3OdDQ3A8B5bMv2WKsEnHsMZ6iDUg==
|
||||||
|
dependencies:
|
||||||
|
"@sendgrid/client" "^7.1.1"
|
||||||
|
"@sendgrid/helpers" "^7.0.1"
|
||||||
|
|
||||||
"@sindresorhus/is@^0.14.0":
|
"@sindresorhus/is@^0.14.0":
|
||||||
version "0.14.0"
|
version "0.14.0"
|
||||||
resolved "https://registry.yarnpkg.com/@sindresorhus/is/-/is-0.14.0.tgz#9fb3a3cf3132328151f353de4632e01e52102bea"
|
resolved "https://registry.yarnpkg.com/@sindresorhus/is/-/is-0.14.0.tgz#9fb3a3cf3132328151f353de4632e01e52102bea"
|
||||||
|
@ -825,6 +863,11 @@ array-equal@^1.0.0:
|
||||||
resolved "https://registry.yarnpkg.com/array-equal/-/array-equal-1.0.0.tgz#8c2a5ef2472fd9ea742b04c77a75093ba2757c93"
|
resolved "https://registry.yarnpkg.com/array-equal/-/array-equal-1.0.0.tgz#8c2a5ef2472fd9ea742b04c77a75093ba2757c93"
|
||||||
integrity sha1-jCpe8kcv2ep0KwTHenUJO6J1fJM=
|
integrity sha1-jCpe8kcv2ep0KwTHenUJO6J1fJM=
|
||||||
|
|
||||||
|
array-filter@^1.0.0:
|
||||||
|
version "1.0.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/array-filter/-/array-filter-1.0.0.tgz#baf79e62e6ef4c2a4c0b831232daffec251f9d83"
|
||||||
|
integrity sha1-uveeYubvTCpMC4MSMtr/7CUfnYM=
|
||||||
|
|
||||||
array-unique@^0.3.2:
|
array-unique@^0.3.2:
|
||||||
version "0.3.2"
|
version "0.3.2"
|
||||||
resolved "https://registry.yarnpkg.com/array-unique/-/array-unique-0.3.2.tgz#a894b75d4bc4f6cd679ef3244a9fd8f46ae2d428"
|
resolved "https://registry.yarnpkg.com/array-unique/-/array-unique-0.3.2.tgz#a894b75d4bc4f6cd679ef3244a9fd8f46ae2d428"
|
||||||
|
@ -897,6 +940,13 @@ atomic-sleep@^1.0.0:
|
||||||
resolved "https://registry.yarnpkg.com/atomic-sleep/-/atomic-sleep-1.0.0.tgz#eb85b77a601fc932cfe432c5acd364a9e2c9075b"
|
resolved "https://registry.yarnpkg.com/atomic-sleep/-/atomic-sleep-1.0.0.tgz#eb85b77a601fc932cfe432c5acd364a9e2c9075b"
|
||||||
integrity sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==
|
integrity sha512-kNOjDqAh7px0XWNI+4QbzoiR/nTkHAWNud2uvnJquD1/x5a7EQZMJT0AczqK0Qn67oY/TTQ1LbUKajZpp3I9tQ==
|
||||||
|
|
||||||
|
available-typed-arrays@^1.0.0, available-typed-arrays@^1.0.2:
|
||||||
|
version "1.0.2"
|
||||||
|
resolved "https://registry.yarnpkg.com/available-typed-arrays/-/available-typed-arrays-1.0.2.tgz#6b098ca9d8039079ee3f77f7b783c4480ba513f5"
|
||||||
|
integrity sha512-XWX3OX8Onv97LMk/ftVyBibpGwY5a8SmuxZPzeOxqmuEqUCOM9ZE+uIaD1VNJ5QnvU2UQusvmKbuM1FR8QWGfQ==
|
||||||
|
dependencies:
|
||||||
|
array-filter "^1.0.0"
|
||||||
|
|
||||||
aws-sign2@~0.7.0:
|
aws-sign2@~0.7.0:
|
||||||
version "0.7.0"
|
version "0.7.0"
|
||||||
resolved "https://registry.yarnpkg.com/aws-sign2/-/aws-sign2-0.7.0.tgz#b46e890934a9591f2d2f6f86d7e6a9f1b3fe76a8"
|
resolved "https://registry.yarnpkg.com/aws-sign2/-/aws-sign2-0.7.0.tgz#b46e890934a9591f2d2f6f86d7e6a9f1b3fe76a8"
|
||||||
|
@ -907,6 +957,13 @@ aws4@^1.8.0:
|
||||||
resolved "https://registry.yarnpkg.com/aws4/-/aws4-1.9.1.tgz#7e33d8f7d449b3f673cd72deb9abdc552dbe528e"
|
resolved "https://registry.yarnpkg.com/aws4/-/aws4-1.9.1.tgz#7e33d8f7d449b3f673cd72deb9abdc552dbe528e"
|
||||||
integrity sha512-wMHVg2EOHaMRxbzgFJ9gtjOOCrI80OHLG14rxi28XwOW8ux6IiEbRCGGGqCtdAIg4FQCbW20k9RsT4y3gJlFug==
|
integrity sha512-wMHVg2EOHaMRxbzgFJ9gtjOOCrI80OHLG14rxi28XwOW8ux6IiEbRCGGGqCtdAIg4FQCbW20k9RsT4y3gJlFug==
|
||||||
|
|
||||||
|
axios@^0.19.2:
|
||||||
|
version "0.19.2"
|
||||||
|
resolved "https://registry.yarnpkg.com/axios/-/axios-0.19.2.tgz#3ea36c5d8818d0d5f8a8a97a6d36b86cdc00cb27"
|
||||||
|
integrity sha512-fjgm5MvRHLhx+osE2xoekY70AhARk3a6hkN+3Io1jc00jtquGvxYlKlsFUhmUET0V5te6CcZI7lcv2Ym61mjHA==
|
||||||
|
dependencies:
|
||||||
|
follow-redirects "1.5.10"
|
||||||
|
|
||||||
babel-jest@^24.9.0:
|
babel-jest@^24.9.0:
|
||||||
version "24.9.0"
|
version "24.9.0"
|
||||||
resolved "https://registry.yarnpkg.com/babel-jest/-/babel-jest-24.9.0.tgz#3fc327cb8467b89d14d7bc70e315104a783ccd54"
|
resolved "https://registry.yarnpkg.com/babel-jest/-/babel-jest-24.9.0.tgz#3fc327cb8467b89d14d7bc70e315104a783ccd54"
|
||||||
|
@ -1567,6 +1624,13 @@ dateformat@^3.0.3:
|
||||||
resolved "https://registry.yarnpkg.com/dateformat/-/dateformat-3.0.3.tgz#a6e37499a4d9a9cf85ef5872044d62901c9889ae"
|
resolved "https://registry.yarnpkg.com/dateformat/-/dateformat-3.0.3.tgz#a6e37499a4d9a9cf85ef5872044d62901c9889ae"
|
||||||
integrity sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==
|
integrity sha512-jyCETtSl3VMZMWeRo7iY1FL19ges1t55hMo5yaam4Jrsm5EPL89UQkoQRyiI+Yf4k8r2ZpdngkV8hr1lIdjb3Q==
|
||||||
|
|
||||||
|
debug@=3.1.0, debug@~3.1.0:
|
||||||
|
version "3.1.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/debug/-/debug-3.1.0.tgz#5bb5a0672628b64149566ba16819e61518c67261"
|
||||||
|
integrity sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==
|
||||||
|
dependencies:
|
||||||
|
ms "2.0.0"
|
||||||
|
|
||||||
debug@^2.2.0, debug@^2.3.3, debug@^2.6.9:
|
debug@^2.2.0, debug@^2.3.3, debug@^2.6.9:
|
||||||
version "2.6.9"
|
version "2.6.9"
|
||||||
resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.9.tgz#5d128515df134ff327e90a4c93f4e077a536341f"
|
resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.9.tgz#5d128515df134ff327e90a4c93f4e077a536341f"
|
||||||
|
@ -1588,13 +1652,6 @@ debug@^4.0.1, debug@^4.1.0, debug@^4.1.1:
|
||||||
dependencies:
|
dependencies:
|
||||||
ms "^2.1.1"
|
ms "^2.1.1"
|
||||||
|
|
||||||
debug@~3.1.0:
|
|
||||||
version "3.1.0"
|
|
||||||
resolved "https://registry.yarnpkg.com/debug/-/debug-3.1.0.tgz#5bb5a0672628b64149566ba16819e61518c67261"
|
|
||||||
integrity sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==
|
|
||||||
dependencies:
|
|
||||||
ms "2.0.0"
|
|
||||||
|
|
||||||
decamelize@^1.2.0:
|
decamelize@^1.2.0:
|
||||||
version "1.2.0"
|
version "1.2.0"
|
||||||
resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-1.2.0.tgz#f6534d15148269b20352e7bee26f501f9a191290"
|
resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-1.2.0.tgz#f6534d15148269b20352e7bee26f501f9a191290"
|
||||||
|
@ -1612,6 +1669,26 @@ decompress-response@^3.3.0:
|
||||||
dependencies:
|
dependencies:
|
||||||
mimic-response "^1.0.0"
|
mimic-response "^1.0.0"
|
||||||
|
|
||||||
|
deep-equal@^2.0.1:
|
||||||
|
version "2.0.3"
|
||||||
|
resolved "https://registry.yarnpkg.com/deep-equal/-/deep-equal-2.0.3.tgz#cad1c15277ad78a5c01c49c2dee0f54de8a6a7b0"
|
||||||
|
integrity sha512-Spqdl4H+ky45I9ByyJtXteOm9CaIrPmnIPmOhrkKGNYWeDgCvJ8jNYVCTjChxW4FqGuZnLHADc8EKRMX6+CgvA==
|
||||||
|
dependencies:
|
||||||
|
es-abstract "^1.17.5"
|
||||||
|
es-get-iterator "^1.1.0"
|
||||||
|
is-arguments "^1.0.4"
|
||||||
|
is-date-object "^1.0.2"
|
||||||
|
is-regex "^1.0.5"
|
||||||
|
isarray "^2.0.5"
|
||||||
|
object-is "^1.1.2"
|
||||||
|
object-keys "^1.1.1"
|
||||||
|
object.assign "^4.1.0"
|
||||||
|
regexp.prototype.flags "^1.3.0"
|
||||||
|
side-channel "^1.0.2"
|
||||||
|
which-boxed-primitive "^1.0.1"
|
||||||
|
which-collection "^1.0.1"
|
||||||
|
which-typed-array "^1.1.2"
|
||||||
|
|
||||||
deep-equal@~1.0.1:
|
deep-equal@~1.0.1:
|
||||||
version "1.0.1"
|
version "1.0.1"
|
||||||
resolved "https://registry.yarnpkg.com/deep-equal/-/deep-equal-1.0.1.tgz#f5d260292b660e084eff4cdbc9f08ad3247448b5"
|
resolved "https://registry.yarnpkg.com/deep-equal/-/deep-equal-1.0.1.tgz#f5d260292b660e084eff4cdbc9f08ad3247448b5"
|
||||||
|
@ -1627,6 +1704,11 @@ deep-is@~0.1.3:
|
||||||
resolved "https://registry.yarnpkg.com/deep-is/-/deep-is-0.1.3.tgz#b369d6fb5dbc13eecf524f91b070feedc357cf34"
|
resolved "https://registry.yarnpkg.com/deep-is/-/deep-is-0.1.3.tgz#b369d6fb5dbc13eecf524f91b070feedc357cf34"
|
||||||
integrity sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=
|
integrity sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=
|
||||||
|
|
||||||
|
deepmerge@^4.2.2:
|
||||||
|
version "4.2.2"
|
||||||
|
resolved "https://registry.yarnpkg.com/deepmerge/-/deepmerge-4.2.2.tgz#44d2ea3679b8f4d4ffba33f03d865fc1e7bf4955"
|
||||||
|
integrity sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==
|
||||||
|
|
||||||
defer-to-connect@^1.0.1:
|
defer-to-connect@^1.0.1:
|
||||||
version "1.1.3"
|
version "1.1.3"
|
||||||
resolved "https://registry.yarnpkg.com/defer-to-connect/-/defer-to-connect-1.1.3.tgz#331ae050c08dcf789f8c83a7b81f0ed94f4ac591"
|
resolved "https://registry.yarnpkg.com/defer-to-connect/-/defer-to-connect-1.1.3.tgz#331ae050c08dcf789f8c83a7b81f0ed94f4ac591"
|
||||||
|
@ -1965,7 +2047,7 @@ error-inject@^1.0.0:
|
||||||
resolved "https://registry.yarnpkg.com/error-inject/-/error-inject-1.0.0.tgz#e2b3d91b54aed672f309d950d154850fa11d4f37"
|
resolved "https://registry.yarnpkg.com/error-inject/-/error-inject-1.0.0.tgz#e2b3d91b54aed672f309d950d154850fa11d4f37"
|
||||||
integrity sha1-4rPZG1Su1nLzCdlQ0VSFD6EdTzc=
|
integrity sha1-4rPZG1Su1nLzCdlQ0VSFD6EdTzc=
|
||||||
|
|
||||||
es-abstract@^1.17.0-next.1, es-abstract@^1.17.2, es-abstract@^1.17.5:
|
es-abstract@^1.17.0-next.1, es-abstract@^1.17.2, es-abstract@^1.17.4, es-abstract@^1.17.5:
|
||||||
version "1.17.5"
|
version "1.17.5"
|
||||||
resolved "https://registry.yarnpkg.com/es-abstract/-/es-abstract-1.17.5.tgz#d8c9d1d66c8981fb9200e2251d799eee92774ae9"
|
resolved "https://registry.yarnpkg.com/es-abstract/-/es-abstract-1.17.5.tgz#d8c9d1d66c8981fb9200e2251d799eee92774ae9"
|
||||||
integrity sha512-BR9auzDbySxOcfog0tLECW8l28eRGpDpU3Dm3Hp4q/N+VtLTmyj4EUN088XZWQDW/hzj6sYRDXeOFsaAODKvpg==
|
integrity sha512-BR9auzDbySxOcfog0tLECW8l28eRGpDpU3Dm3Hp4q/N+VtLTmyj4EUN088XZWQDW/hzj6sYRDXeOFsaAODKvpg==
|
||||||
|
@ -1982,6 +2064,19 @@ es-abstract@^1.17.0-next.1, es-abstract@^1.17.2, es-abstract@^1.17.5:
|
||||||
string.prototype.trimleft "^2.1.1"
|
string.prototype.trimleft "^2.1.1"
|
||||||
string.prototype.trimright "^2.1.1"
|
string.prototype.trimright "^2.1.1"
|
||||||
|
|
||||||
|
es-get-iterator@^1.1.0:
|
||||||
|
version "1.1.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/es-get-iterator/-/es-get-iterator-1.1.0.tgz#bb98ad9d6d63b31aacdc8f89d5d0ee57bcb5b4c8"
|
||||||
|
integrity sha512-UfrmHuWQlNMTs35e1ypnvikg6jCz3SK8v8ImvmDsh36fCVUR1MqoFDiyn0/k52C8NqO3YsO8Oe0azeesNuqSsQ==
|
||||||
|
dependencies:
|
||||||
|
es-abstract "^1.17.4"
|
||||||
|
has-symbols "^1.0.1"
|
||||||
|
is-arguments "^1.0.4"
|
||||||
|
is-map "^2.0.1"
|
||||||
|
is-set "^2.0.1"
|
||||||
|
is-string "^1.0.5"
|
||||||
|
isarray "^2.0.5"
|
||||||
|
|
||||||
es-to-primitive@^1.2.1:
|
es-to-primitive@^1.2.1:
|
||||||
version "1.2.1"
|
version "1.2.1"
|
||||||
resolved "https://registry.yarnpkg.com/es-to-primitive/-/es-to-primitive-1.2.1.tgz#e55cd4c9cdc188bcefb03b366c736323fc5c898a"
|
resolved "https://registry.yarnpkg.com/es-to-primitive/-/es-to-primitive-1.2.1.tgz#e55cd4c9cdc188bcefb03b366c736323fc5c898a"
|
||||||
|
@ -2444,6 +2539,13 @@ flatted@^2.0.0:
|
||||||
resolved "https://registry.yarnpkg.com/flatted/-/flatted-2.0.2.tgz#4575b21e2bcee7434aa9be662f4b7b5f9c2b5138"
|
resolved "https://registry.yarnpkg.com/flatted/-/flatted-2.0.2.tgz#4575b21e2bcee7434aa9be662f4b7b5f9c2b5138"
|
||||||
integrity sha512-r5wGx7YeOwNWNlCA0wQ86zKyDLMQr+/RB8xy74M4hTphfmjlijTSSXGuH8rnvKZnfT9i+75zmd8jcKdMR4O6jA==
|
integrity sha512-r5wGx7YeOwNWNlCA0wQ86zKyDLMQr+/RB8xy74M4hTphfmjlijTSSXGuH8rnvKZnfT9i+75zmd8jcKdMR4O6jA==
|
||||||
|
|
||||||
|
follow-redirects@1.5.10:
|
||||||
|
version "1.5.10"
|
||||||
|
resolved "https://registry.yarnpkg.com/follow-redirects/-/follow-redirects-1.5.10.tgz#7b7a9f9aea2fdff36786a94ff643ed07f4ff5e2a"
|
||||||
|
integrity sha512-0V5l4Cizzvqt5D44aTXbFZz+FtyXV1vrDN6qrelxtfYQKW0KO0W2T/hkE8xvGa/540LkZlkaUjO4ailYTFtHVQ==
|
||||||
|
dependencies:
|
||||||
|
debug "=3.1.0"
|
||||||
|
|
||||||
for-in@^1.0.2:
|
for-in@^1.0.2:
|
||||||
version "1.0.2"
|
version "1.0.2"
|
||||||
resolved "https://registry.yarnpkg.com/for-in/-/for-in-1.0.2.tgz#81068d295a8142ec0ac726c6e2200c30fb6d5e80"
|
resolved "https://registry.yarnpkg.com/for-in/-/for-in-1.0.2.tgz#81068d295a8142ec0ac726c6e2200c30fb6d5e80"
|
||||||
|
@ -2967,11 +3069,21 @@ is-accessor-descriptor@^1.0.0:
|
||||||
dependencies:
|
dependencies:
|
||||||
kind-of "^6.0.0"
|
kind-of "^6.0.0"
|
||||||
|
|
||||||
|
is-arguments@^1.0.4:
|
||||||
|
version "1.0.4"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-arguments/-/is-arguments-1.0.4.tgz#3faf966c7cba0ff437fb31f6250082fcf0448cf3"
|
||||||
|
integrity sha512-xPh0Rmt8NE65sNzvyUmWgI1tz3mKq74lGA0mL8LYZcoIzKOzDh6HmrYm3d18k60nHerC8A9Km8kYu87zfSFnLA==
|
||||||
|
|
||||||
is-arrayish@^0.2.1:
|
is-arrayish@^0.2.1:
|
||||||
version "0.2.1"
|
version "0.2.1"
|
||||||
resolved "https://registry.yarnpkg.com/is-arrayish/-/is-arrayish-0.2.1.tgz#77c99840527aa8ecb1a8ba697b80645a7a926a9d"
|
resolved "https://registry.yarnpkg.com/is-arrayish/-/is-arrayish-0.2.1.tgz#77c99840527aa8ecb1a8ba697b80645a7a926a9d"
|
||||||
integrity sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=
|
integrity sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=
|
||||||
|
|
||||||
|
is-bigint@^1.0.0:
|
||||||
|
version "1.0.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-bigint/-/is-bigint-1.0.0.tgz#73da8c33208d00f130e9b5e15d23eac9215601c4"
|
||||||
|
integrity sha512-t5mGUXC/xRheCK431ylNiSkGGpBp8bHENBcENTkDT6ppwPzEVxNGZRvgvmOEfbWkFhA7D2GEuE2mmQTr78sl2g==
|
||||||
|
|
||||||
is-binary-path@~2.1.0:
|
is-binary-path@~2.1.0:
|
||||||
version "2.1.0"
|
version "2.1.0"
|
||||||
resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-2.1.0.tgz#ea1f7f3b80f064236e83470f86c09c254fb45b09"
|
resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-2.1.0.tgz#ea1f7f3b80f064236e83470f86c09c254fb45b09"
|
||||||
|
@ -2979,6 +3091,11 @@ is-binary-path@~2.1.0:
|
||||||
dependencies:
|
dependencies:
|
||||||
binary-extensions "^2.0.0"
|
binary-extensions "^2.0.0"
|
||||||
|
|
||||||
|
is-boolean-object@^1.0.0:
|
||||||
|
version "1.0.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-boolean-object/-/is-boolean-object-1.0.1.tgz#10edc0900dd127697a92f6f9807c7617d68ac48e"
|
||||||
|
integrity sha512-TqZuVwa/sppcrhUCAYkGBk7w0yxfQQnxq28fjkO53tnK9FQXmdwz2JS5+GjsWQ6RByES1K40nI+yDic5c9/aAQ==
|
||||||
|
|
||||||
is-buffer@^1.1.5:
|
is-buffer@^1.1.5:
|
||||||
version "1.1.6"
|
version "1.1.6"
|
||||||
resolved "https://registry.yarnpkg.com/is-buffer/-/is-buffer-1.1.6.tgz#efaa2ea9daa0d7ab2ea13a97b2b8ad51fefbe8be"
|
resolved "https://registry.yarnpkg.com/is-buffer/-/is-buffer-1.1.6.tgz#efaa2ea9daa0d7ab2ea13a97b2b8ad51fefbe8be"
|
||||||
|
@ -3015,7 +3132,7 @@ is-data-descriptor@^1.0.0:
|
||||||
dependencies:
|
dependencies:
|
||||||
kind-of "^6.0.0"
|
kind-of "^6.0.0"
|
||||||
|
|
||||||
is-date-object@^1.0.1:
|
is-date-object@^1.0.1, is-date-object@^1.0.2:
|
||||||
version "1.0.2"
|
version "1.0.2"
|
||||||
resolved "https://registry.yarnpkg.com/is-date-object/-/is-date-object-1.0.2.tgz#bda736f2cd8fd06d32844e7743bfa7494c3bfd7e"
|
resolved "https://registry.yarnpkg.com/is-date-object/-/is-date-object-1.0.2.tgz#bda736f2cd8fd06d32844e7743bfa7494c3bfd7e"
|
||||||
integrity sha512-USlDT524woQ08aoZFzh3/Z6ch9Y/EWXEHQ/AaRN0SkKq4t2Jw2R2339tSXmwuVoY7LLlBCbOIlx2myP/L5zk0g==
|
integrity sha512-USlDT524woQ08aoZFzh3/Z6ch9Y/EWXEHQ/AaRN0SkKq4t2Jw2R2339tSXmwuVoY7LLlBCbOIlx2myP/L5zk0g==
|
||||||
|
@ -3090,11 +3207,21 @@ is-installed-globally@^0.3.1:
|
||||||
global-dirs "^2.0.1"
|
global-dirs "^2.0.1"
|
||||||
is-path-inside "^3.0.1"
|
is-path-inside "^3.0.1"
|
||||||
|
|
||||||
|
is-map@^2.0.1:
|
||||||
|
version "2.0.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-map/-/is-map-2.0.1.tgz#520dafc4307bb8ebc33b813de5ce7c9400d644a1"
|
||||||
|
integrity sha512-T/S49scO8plUiAOA2DBTBG3JHpn1yiw0kRp6dgiZ0v2/6twi5eiB0rHtHFH9ZIrvlWc6+4O+m4zg5+Z833aXgw==
|
||||||
|
|
||||||
is-npm@^4.0.0:
|
is-npm@^4.0.0:
|
||||||
version "4.0.0"
|
version "4.0.0"
|
||||||
resolved "https://registry.yarnpkg.com/is-npm/-/is-npm-4.0.0.tgz#c90dd8380696df87a7a6d823c20d0b12bbe3c84d"
|
resolved "https://registry.yarnpkg.com/is-npm/-/is-npm-4.0.0.tgz#c90dd8380696df87a7a6d823c20d0b12bbe3c84d"
|
||||||
integrity sha512-96ECIfh9xtDDlPylNPXhzjsykHsMJZ18ASpaWzQyBr4YRTcVjUvzaHayDAES2oU/3KpljhHUjtSRNiDwi0F0ig==
|
integrity sha512-96ECIfh9xtDDlPylNPXhzjsykHsMJZ18ASpaWzQyBr4YRTcVjUvzaHayDAES2oU/3KpljhHUjtSRNiDwi0F0ig==
|
||||||
|
|
||||||
|
is-number-object@^1.0.3:
|
||||||
|
version "1.0.4"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-number-object/-/is-number-object-1.0.4.tgz#36ac95e741cf18b283fc1ddf5e83da798e3ec197"
|
||||||
|
integrity sha512-zohwelOAur+5uXtk8O3GPQ1eAcu4ZX3UwxQhUlfFFMNpUd83gXgjbhJh6HmB6LUNV/ieOLQuDwJO3dWJosUeMw==
|
||||||
|
|
||||||
is-number@^3.0.0:
|
is-number@^3.0.0:
|
||||||
version "3.0.0"
|
version "3.0.0"
|
||||||
resolved "https://registry.yarnpkg.com/is-number/-/is-number-3.0.0.tgz#24fd6201a4782cf50561c810276afc7d12d71195"
|
resolved "https://registry.yarnpkg.com/is-number/-/is-number-3.0.0.tgz#24fd6201a4782cf50561c810276afc7d12d71195"
|
||||||
|
@ -3131,11 +3258,21 @@ is-regex@^1.0.5:
|
||||||
dependencies:
|
dependencies:
|
||||||
has "^1.0.3"
|
has "^1.0.3"
|
||||||
|
|
||||||
|
is-set@^2.0.1:
|
||||||
|
version "2.0.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-set/-/is-set-2.0.1.tgz#d1604afdab1724986d30091575f54945da7e5f43"
|
||||||
|
integrity sha512-eJEzOtVyenDs1TMzSQ3kU3K+E0GUS9sno+F0OBT97xsgcJsF9nXMBtkT9/kut5JEpM7oL7X/0qxR17K3mcwIAA==
|
||||||
|
|
||||||
is-stream@^1.1.0:
|
is-stream@^1.1.0:
|
||||||
version "1.1.0"
|
version "1.1.0"
|
||||||
resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-1.1.0.tgz#12d4a3dd4e68e0b79ceb8dbc84173ae80d91ca44"
|
resolved "https://registry.yarnpkg.com/is-stream/-/is-stream-1.1.0.tgz#12d4a3dd4e68e0b79ceb8dbc84173ae80d91ca44"
|
||||||
integrity sha1-EtSj3U5o4Lec6428hBc66A2RykQ=
|
integrity sha1-EtSj3U5o4Lec6428hBc66A2RykQ=
|
||||||
|
|
||||||
|
is-string@^1.0.4, is-string@^1.0.5:
|
||||||
|
version "1.0.5"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-string/-/is-string-1.0.5.tgz#40493ed198ef3ff477b8c7f92f644ec82a5cd3a6"
|
||||||
|
integrity sha512-buY6VNRjhQMiF1qWDouloZlQbRhDPCebwxSjxMjxgemYT46YMd2NR0/H+fBhEfWX4A/w9TBJ+ol+okqJKFE6vQ==
|
||||||
|
|
||||||
is-symbol@^1.0.2:
|
is-symbol@^1.0.2:
|
||||||
version "1.0.3"
|
version "1.0.3"
|
||||||
resolved "https://registry.yarnpkg.com/is-symbol/-/is-symbol-1.0.3.tgz#38e1014b9e6329be0de9d24a414fd7441ec61937"
|
resolved "https://registry.yarnpkg.com/is-symbol/-/is-symbol-1.0.3.tgz#38e1014b9e6329be0de9d24a414fd7441ec61937"
|
||||||
|
@ -3152,11 +3289,31 @@ is-type-of@^1.0.0:
|
||||||
is-class-hotfix "~0.0.6"
|
is-class-hotfix "~0.0.6"
|
||||||
isstream "~0.1.2"
|
isstream "~0.1.2"
|
||||||
|
|
||||||
|
is-typed-array@^1.1.3:
|
||||||
|
version "1.1.3"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-typed-array/-/is-typed-array-1.1.3.tgz#a4ff5a5e672e1a55f99c7f54e59597af5c1df04d"
|
||||||
|
integrity sha512-BSYUBOK/HJibQ30wWkWold5txYwMUXQct9YHAQJr8fSwvZoiglcqB0pd7vEN23+Tsi9IUEjztdOSzl4qLVYGTQ==
|
||||||
|
dependencies:
|
||||||
|
available-typed-arrays "^1.0.0"
|
||||||
|
es-abstract "^1.17.4"
|
||||||
|
foreach "^2.0.5"
|
||||||
|
has-symbols "^1.0.1"
|
||||||
|
|
||||||
is-typedarray@^1.0.0, is-typedarray@~1.0.0:
|
is-typedarray@^1.0.0, is-typedarray@~1.0.0:
|
||||||
version "1.0.0"
|
version "1.0.0"
|
||||||
resolved "https://registry.yarnpkg.com/is-typedarray/-/is-typedarray-1.0.0.tgz#e479c80858df0c1b11ddda6940f96011fcda4a9a"
|
resolved "https://registry.yarnpkg.com/is-typedarray/-/is-typedarray-1.0.0.tgz#e479c80858df0c1b11ddda6940f96011fcda4a9a"
|
||||||
integrity sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=
|
integrity sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=
|
||||||
|
|
||||||
|
is-weakmap@^2.0.1:
|
||||||
|
version "2.0.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-weakmap/-/is-weakmap-2.0.1.tgz#5008b59bdc43b698201d18f62b37b2ca243e8cf2"
|
||||||
|
integrity sha512-NSBR4kH5oVj1Uwvv970ruUkCV7O1mzgVFO4/rev2cLRda9Tm9HrL70ZPut4rOHgY0FNrUu9BCbXA2sdQ+x0chA==
|
||||||
|
|
||||||
|
is-weakset@^2.0.1:
|
||||||
|
version "2.0.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/is-weakset/-/is-weakset-2.0.1.tgz#e9a0af88dbd751589f5e50d80f4c98b780884f83"
|
||||||
|
integrity sha512-pi4vhbhVHGLxohUw7PhGsueT4vRGFoXhP7+RGN0jKIv9+8PWYCQTqtADngrxOm2g46hoH0+g8uZZBzMrvVGDmw==
|
||||||
|
|
||||||
is-windows@^1.0.2:
|
is-windows@^1.0.2:
|
||||||
version "1.0.2"
|
version "1.0.2"
|
||||||
resolved "https://registry.yarnpkg.com/is-windows/-/is-windows-1.0.2.tgz#d1850eb9791ecd18e6182ce12a30f396634bb19d"
|
resolved "https://registry.yarnpkg.com/is-windows/-/is-windows-1.0.2.tgz#d1850eb9791ecd18e6182ce12a30f396634bb19d"
|
||||||
|
@ -3182,6 +3339,11 @@ isarray@1.0.0, isarray@~1.0.0:
|
||||||
resolved "https://registry.yarnpkg.com/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11"
|
resolved "https://registry.yarnpkg.com/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11"
|
||||||
integrity sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=
|
integrity sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=
|
||||||
|
|
||||||
|
isarray@^2.0.5:
|
||||||
|
version "2.0.5"
|
||||||
|
resolved "https://registry.yarnpkg.com/isarray/-/isarray-2.0.5.tgz#8af1e4c1221244cc62459faf38940d4e644a5723"
|
||||||
|
integrity sha512-xHjhDr3cNBK0BzdUJSPXZntQUx/mwMS5Rw4A7lPJ90XGAO6ISP/ePDNuo0vhqOZU+UD5JoodwCAAoZQd3FeAKw==
|
||||||
|
|
||||||
isbinaryfile@^4.0.6:
|
isbinaryfile@^4.0.6:
|
||||||
version "4.0.6"
|
version "4.0.6"
|
||||||
resolved "https://registry.yarnpkg.com/isbinaryfile/-/isbinaryfile-4.0.6.tgz#edcb62b224e2b4710830b67498c8e4e5a4d2610b"
|
resolved "https://registry.yarnpkg.com/isbinaryfile/-/isbinaryfile-4.0.6.tgz#edcb62b224e2b4710830b67498c8e4e5a4d2610b"
|
||||||
|
@ -4589,6 +4751,14 @@ object-inspect@^1.7.0:
|
||||||
resolved "https://registry.yarnpkg.com/object-inspect/-/object-inspect-1.7.0.tgz#f4f6bd181ad77f006b5ece60bd0b6f398ff74a67"
|
resolved "https://registry.yarnpkg.com/object-inspect/-/object-inspect-1.7.0.tgz#f4f6bd181ad77f006b5ece60bd0b6f398ff74a67"
|
||||||
integrity sha512-a7pEHdh1xKIAgTySUGgLMx/xwDZskN1Ud6egYYN3EdRW4ZMPNEDUTF+hwy2LUC+Bl+SyLXANnwz/jyh/qutKUw==
|
integrity sha512-a7pEHdh1xKIAgTySUGgLMx/xwDZskN1Ud6egYYN3EdRW4ZMPNEDUTF+hwy2LUC+Bl+SyLXANnwz/jyh/qutKUw==
|
||||||
|
|
||||||
|
object-is@^1.1.2:
|
||||||
|
version "1.1.2"
|
||||||
|
resolved "https://registry.yarnpkg.com/object-is/-/object-is-1.1.2.tgz#c5d2e87ff9e119f78b7a088441519e2eec1573b6"
|
||||||
|
integrity sha512-5lHCz+0uufF6wZ7CRFWJN3hp8Jqblpgve06U5CMQ3f//6iDjPr2PEo9MWCjEssDsa+UZEL4PkFpr+BMop6aKzQ==
|
||||||
|
dependencies:
|
||||||
|
define-properties "^1.1.3"
|
||||||
|
es-abstract "^1.17.5"
|
||||||
|
|
||||||
object-keys@^1.0.11, object-keys@^1.0.12, object-keys@^1.0.6, object-keys@^1.1.1:
|
object-keys@^1.0.11, object-keys@^1.0.12, object-keys@^1.0.6, object-keys@^1.1.1:
|
||||||
version "1.1.1"
|
version "1.1.1"
|
||||||
resolved "https://registry.yarnpkg.com/object-keys/-/object-keys-1.1.1.tgz#1c47f272df277f3b1daf061677d9c82e2322c60e"
|
resolved "https://registry.yarnpkg.com/object-keys/-/object-keys-1.1.1.tgz#1c47f272df277f3b1daf061677d9c82e2322c60e"
|
||||||
|
@ -5310,6 +5480,19 @@ regex-not@^1.0.0, regex-not@^1.0.2:
|
||||||
extend-shallow "^3.0.2"
|
extend-shallow "^3.0.2"
|
||||||
safe-regex "^1.1.0"
|
safe-regex "^1.1.0"
|
||||||
|
|
||||||
|
regexp.prototype.flags@^1.3.0:
|
||||||
|
version "1.3.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/regexp.prototype.flags/-/regexp.prototype.flags-1.3.0.tgz#7aba89b3c13a64509dabcf3ca8d9fbb9bdf5cb75"
|
||||||
|
integrity sha512-2+Q0C5g951OlYlJz6yu5/M33IcsESLlLfsyIaLJaG4FA2r4yP8MvVMJUUP/fVBkSpbbbZlS5gynbEWLipiiXiQ==
|
||||||
|
dependencies:
|
||||||
|
define-properties "^1.1.3"
|
||||||
|
es-abstract "^1.17.0-next.1"
|
||||||
|
|
||||||
|
regexparam@^1.3.0:
|
||||||
|
version "1.3.0"
|
||||||
|
resolved "https://registry.yarnpkg.com/regexparam/-/regexparam-1.3.0.tgz#2fe42c93e32a40eff6235d635e0ffa344b92965f"
|
||||||
|
integrity sha512-6IQpFBv6e5vz1QAqI+V4k8P2e/3gRrqfCJ9FI+O1FLQTO+Uz6RXZEZOPmTJ6hlGj7gkERzY5BRCv09whKP96/g==
|
||||||
|
|
||||||
regexpp@^2.0.1:
|
regexpp@^2.0.1:
|
||||||
version "2.0.1"
|
version "2.0.1"
|
||||||
resolved "https://registry.yarnpkg.com/regexpp/-/regexpp-2.0.1.tgz#8d19d31cf632482b589049f8281f93dbcba4d07f"
|
resolved "https://registry.yarnpkg.com/regexpp/-/regexpp-2.0.1.tgz#8d19d31cf632482b589049f8281f93dbcba4d07f"
|
||||||
|
@ -5638,6 +5821,14 @@ shortid@^2.2.8:
|
||||||
dependencies:
|
dependencies:
|
||||||
nanoid "^2.1.0"
|
nanoid "^2.1.0"
|
||||||
|
|
||||||
|
side-channel@^1.0.2:
|
||||||
|
version "1.0.2"
|
||||||
|
resolved "https://registry.yarnpkg.com/side-channel/-/side-channel-1.0.2.tgz#df5d1abadb4e4bf4af1cd8852bf132d2f7876947"
|
||||||
|
integrity sha512-7rL9YlPHg7Ancea1S96Pa8/QWb4BtXL/TZvS6B8XFetGBeuhAsfmUspK6DokBeZ64+Kj9TCNRD/30pVz1BvQNA==
|
||||||
|
dependencies:
|
||||||
|
es-abstract "^1.17.0-next.1"
|
||||||
|
object-inspect "^1.7.0"
|
||||||
|
|
||||||
signal-exit@^3.0.0, signal-exit@^3.0.2:
|
signal-exit@^3.0.0, signal-exit@^3.0.2:
|
||||||
version "3.0.3"
|
version "3.0.3"
|
||||||
resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.3.tgz#a1410c2edd8f077b08b4e253c8eacfcaf057461c"
|
resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.3.tgz#a1410c2edd8f077b08b4e253c8eacfcaf057461c"
|
||||||
|
@ -6046,6 +6237,11 @@ supports-color@^7.1.0:
|
||||||
dependencies:
|
dependencies:
|
||||||
has-flag "^4.0.0"
|
has-flag "^4.0.0"
|
||||||
|
|
||||||
|
svelte@^3.9.2:
|
||||||
|
version "3.22.3"
|
||||||
|
resolved "https://registry.yarnpkg.com/svelte/-/svelte-3.22.3.tgz#6af3bdcfea44c2fadbf17a32c479f49bdf1aba4b"
|
||||||
|
integrity sha512-DumSy5eWPFPlMUGf3+eHyFSkt5yLqyAmMdCuXOE4qc5GtFyLxwTAGKZmgKmW2jmbpTTeFQ/fSQfDBQbl9Eo7yw==
|
||||||
|
|
||||||
symbol-tree@^3.2.2:
|
symbol-tree@^3.2.2:
|
||||||
version "3.2.4"
|
version "3.2.4"
|
||||||
resolved "https://registry.yarnpkg.com/symbol-tree/-/symbol-tree-3.2.4.tgz#430637d248ba77e078883951fb9aa0eed7c63fa2"
|
resolved "https://registry.yarnpkg.com/symbol-tree/-/symbol-tree-3.2.4.tgz#430637d248ba77e078883951fb9aa0eed7c63fa2"
|
||||||
|
@ -6526,11 +6722,44 @@ whatwg-url@^7.0.0:
|
||||||
tr46 "^1.0.1"
|
tr46 "^1.0.1"
|
||||||
webidl-conversions "^4.0.2"
|
webidl-conversions "^4.0.2"
|
||||||
|
|
||||||
|
which-boxed-primitive@^1.0.1:
|
||||||
|
version "1.0.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/which-boxed-primitive/-/which-boxed-primitive-1.0.1.tgz#cbe8f838ebe91ba2471bb69e9edbda67ab5a5ec1"
|
||||||
|
integrity sha512-7BT4TwISdDGBgaemWU0N0OU7FeAEJ9Oo2P1PHRm/FCWoEi2VLWC9b6xvxAA3C/NMpxg3HXVgi0sMmGbNUbNepQ==
|
||||||
|
dependencies:
|
||||||
|
is-bigint "^1.0.0"
|
||||||
|
is-boolean-object "^1.0.0"
|
||||||
|
is-number-object "^1.0.3"
|
||||||
|
is-string "^1.0.4"
|
||||||
|
is-symbol "^1.0.2"
|
||||||
|
|
||||||
|
which-collection@^1.0.1:
|
||||||
|
version "1.0.1"
|
||||||
|
resolved "https://registry.yarnpkg.com/which-collection/-/which-collection-1.0.1.tgz#70eab71ebbbd2aefaf32f917082fc62cdcb70906"
|
||||||
|
integrity sha512-W8xeTUwaln8i3K/cY1nGXzdnVZlidBcagyNFtBdD5kxnb4TvGKR7FfSIS3mYpwWS1QUCutfKz8IY8RjftB0+1A==
|
||||||
|
dependencies:
|
||||||
|
is-map "^2.0.1"
|
||||||
|
is-set "^2.0.1"
|
||||||
|
is-weakmap "^2.0.1"
|
||||||
|
is-weakset "^2.0.1"
|
||||||
|
|
||||||
which-module@^2.0.0:
|
which-module@^2.0.0:
|
||||||
version "2.0.0"
|
version "2.0.0"
|
||||||
resolved "https://registry.yarnpkg.com/which-module/-/which-module-2.0.0.tgz#d9ef07dce77b9902b8a3a8fa4b31c3e3f7e6e87a"
|
resolved "https://registry.yarnpkg.com/which-module/-/which-module-2.0.0.tgz#d9ef07dce77b9902b8a3a8fa4b31c3e3f7e6e87a"
|
||||||
integrity sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=
|
integrity sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=
|
||||||
|
|
||||||
|
which-typed-array@^1.1.2:
|
||||||
|
version "1.1.2"
|
||||||
|
resolved "https://registry.yarnpkg.com/which-typed-array/-/which-typed-array-1.1.2.tgz#e5f98e56bda93e3dac196b01d47c1156679c00b2"
|
||||||
|
integrity sha512-KT6okrd1tE6JdZAy3o2VhMoYPh3+J6EMZLyrxBQsZflI1QCZIxMrIYLkosd8Twf+YfknVIHmYQPgJt238p8dnQ==
|
||||||
|
dependencies:
|
||||||
|
available-typed-arrays "^1.0.2"
|
||||||
|
es-abstract "^1.17.5"
|
||||||
|
foreach "^2.0.5"
|
||||||
|
function-bind "^1.1.1"
|
||||||
|
has-symbols "^1.0.1"
|
||||||
|
is-typed-array "^1.1.3"
|
||||||
|
|
||||||
which@^1.2.9, which@^1.3.0:
|
which@^1.2.9, which@^1.3.0:
|
||||||
version "1.3.1"
|
version "1.3.1"
|
||||||
resolved "https://registry.yarnpkg.com/which/-/which-1.3.1.tgz#a45043d54f5805316da8d62f9f50918d3da70b0a"
|
resolved "https://registry.yarnpkg.com/which/-/which-1.3.1.tgz#a45043d54f5805316da8d62f9f50918d3da70b0a"
|
||||||
|
|
|
@ -12,10 +12,10 @@
|
||||||
"props": {
|
"props": {
|
||||||
"logoUrl": "string",
|
"logoUrl": "string",
|
||||||
"title": "string",
|
"title": "string",
|
||||||
"backgroundColor": "colour",
|
"backgroundColor": "string",
|
||||||
"color": "colour",
|
"color": "string",
|
||||||
"borderWidth": "string",
|
"borderWidth": "string",
|
||||||
"borderColor": "colour",
|
"borderColor": "string",
|
||||||
"borderStyle": "string"
|
"borderStyle": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
@ -23,35 +23,10 @@
|
||||||
"name": "Button",
|
"name": "Button",
|
||||||
"description": "an html <button />",
|
"description": "an html <button />",
|
||||||
"props": {
|
"props": {
|
||||||
"contentText": {
|
"text": "string",
|
||||||
"type": "string",
|
|
||||||
"default": "Button"
|
|
||||||
},
|
|
||||||
"className": "string",
|
"className": "string",
|
||||||
"disabled": "bool",
|
"disabled": "bool",
|
||||||
"onClick": "event",
|
"onClick": "event"
|
||||||
"background": "colour",
|
|
||||||
"color": "colour",
|
|
||||||
"border": "string",
|
|
||||||
"padding": "string",
|
|
||||||
"hoverColor": "string",
|
|
||||||
"hoverBackground": "string",
|
|
||||||
"hoverBorder": "string",
|
|
||||||
"fontFamily": {
|
|
||||||
"type": "options",
|
|
||||||
"default": "initial",
|
|
||||||
"styleBindingProperty": "font-family",
|
|
||||||
"options": [
|
|
||||||
"initial",
|
|
||||||
"Times New Roman",
|
|
||||||
"Georgia",
|
|
||||||
"Arial",
|
|
||||||
"Arial Black",
|
|
||||||
"Comic Sans MS",
|
|
||||||
"Impact",
|
|
||||||
"Lucida Sans Unicode"
|
|
||||||
]
|
|
||||||
}
|
|
||||||
},
|
},
|
||||||
"tags": [
|
"tags": [
|
||||||
"layout"
|
"layout"
|
||||||
|
@ -167,58 +142,7 @@
|
||||||
"children": false,
|
"children": false,
|
||||||
"props": {
|
"props": {
|
||||||
"text": "string",
|
"text": "string",
|
||||||
"color": "colour",
|
"type": {"type": "string", "default": "none"}
|
||||||
"fontFamily": {
|
|
||||||
"type": "options",
|
|
||||||
"default": "initial",
|
|
||||||
"styleBindingProperty": "font-family",
|
|
||||||
"options": [
|
|
||||||
"initial",
|
|
||||||
"Times New Roman",
|
|
||||||
"Georgia",
|
|
||||||
"Arial",
|
|
||||||
"Arial Black",
|
|
||||||
"Comic Sans MS",
|
|
||||||
"Impact",
|
|
||||||
"Lucida Sans Unicode"
|
|
||||||
]
|
|
||||||
},
|
|
||||||
"fontSize": "string",
|
|
||||||
"textAlign": {
|
|
||||||
"type": "options",
|
|
||||||
"default": "inline",
|
|
||||||
"options": [
|
|
||||||
"left",
|
|
||||||
"center",
|
|
||||||
"right"
|
|
||||||
]
|
|
||||||
},
|
|
||||||
"verticalAlign": {
|
|
||||||
"type": "options",
|
|
||||||
"default": "inline",
|
|
||||||
"options": [
|
|
||||||
"top",
|
|
||||||
"middle",
|
|
||||||
"bottom"
|
|
||||||
]
|
|
||||||
},
|
|
||||||
"formattingTag": {
|
|
||||||
"type": "options",
|
|
||||||
"default": "none",
|
|
||||||
"options": [
|
|
||||||
"none",
|
|
||||||
"<b> - bold",
|
|
||||||
"<strong> - important",
|
|
||||||
"<i> - italic",
|
|
||||||
"<em> - emphasized",
|
|
||||||
"<mark> - marked text",
|
|
||||||
"<small> - small",
|
|
||||||
"<del> - deleted",
|
|
||||||
"<ins> - inserted",
|
|
||||||
"<sub> - subscript",
|
|
||||||
"<sup> - superscript"
|
|
||||||
]
|
|
||||||
}
|
|
||||||
},
|
},
|
||||||
"tags": [
|
"tags": [
|
||||||
"div",
|
"div",
|
||||||
|
@ -230,6 +154,7 @@
|
||||||
"description": "A component that allows the user to input text.",
|
"description": "A component that allows the user to input text.",
|
||||||
"props": {
|
"props": {
|
||||||
"label": "string",
|
"label": "string",
|
||||||
|
"type": "string",
|
||||||
"value": "string",
|
"value": "string",
|
||||||
"onchange": "event"
|
"onchange": "event"
|
||||||
}
|
}
|
||||||
|
@ -259,7 +184,7 @@
|
||||||
"props": {
|
"props": {
|
||||||
"icon": "string",
|
"icon": "string",
|
||||||
"fontSize": "string",
|
"fontSize": "string",
|
||||||
"color": "colour"
|
"color": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"datatable": {
|
"datatable": {
|
||||||
|
@ -328,8 +253,8 @@
|
||||||
"url": "string",
|
"url": "string",
|
||||||
"openInNewTab": "bool",
|
"openInNewTab": "bool",
|
||||||
"text": "string",
|
"text": "string",
|
||||||
"color": "colour",
|
"color": "string",
|
||||||
"hoverColor": "colour",
|
"hoverColor": "string",
|
||||||
"underline": "bool",
|
"underline": "bool",
|
||||||
"fontSize": "string",
|
"fontSize": "string",
|
||||||
"fontFamily": {
|
"fontFamily": {
|
||||||
|
@ -383,25 +308,6 @@
|
||||||
"summary"
|
"summary"
|
||||||
],
|
],
|
||||||
"default": "div"
|
"default": "div"
|
||||||
},
|
|
||||||
"backgroundColor": "string",
|
|
||||||
"color": "string",
|
|
||||||
"borderWidth": "string",
|
|
||||||
"borderColor": "string",
|
|
||||||
"borderStyle": {
|
|
||||||
"type": "options",
|
|
||||||
"options": [
|
|
||||||
"none",
|
|
||||||
"solid",
|
|
||||||
"dotted",
|
|
||||||
"dashed",
|
|
||||||
"double",
|
|
||||||
"groove",
|
|
||||||
"ridge",
|
|
||||||
"inset",
|
|
||||||
"outset"
|
|
||||||
],
|
|
||||||
"default": "none"
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"container": true,
|
"container": true,
|
||||||
|
@ -416,7 +322,6 @@
|
||||||
"description": "An HTML H1 - H6 tag",
|
"description": "An HTML H1 - H6 tag",
|
||||||
"props": {
|
"props": {
|
||||||
"className": "string",
|
"className": "string",
|
||||||
"color":"colour",
|
|
||||||
"text": "string",
|
"text": "string",
|
||||||
"type": {
|
"type": {
|
||||||
"type": "options",
|
"type": "options",
|
||||||
|
@ -429,21 +334,6 @@
|
||||||
"h5",
|
"h5",
|
||||||
"h6"
|
"h6"
|
||||||
]
|
]
|
||||||
},
|
|
||||||
"fontFamily": {
|
|
||||||
"type": "options",
|
|
||||||
"default": "initial",
|
|
||||||
"styleBindingProperty": "font-family",
|
|
||||||
"options": [
|
|
||||||
"initial",
|
|
||||||
"Times New Roman",
|
|
||||||
"Georgia",
|
|
||||||
"Arial",
|
|
||||||
"Arial Black",
|
|
||||||
"Comic Sans MS",
|
|
||||||
"Impact",
|
|
||||||
"Lucida Sans Unicode"
|
|
||||||
]
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"tags": []
|
"tags": []
|
||||||
|
|
|
@ -1,58 +1,15 @@
|
||||||
<script>
|
<script>
|
||||||
import { cssVars, createClasses } from "./cssVars"
|
|
||||||
import { buildStyle } from "./buildStyle"
|
|
||||||
export let className = "default"
|
export let className = "default"
|
||||||
export let disabled = false
|
export let disabled = false
|
||||||
export let contentText
|
export let text
|
||||||
export let onClick
|
export let onClick
|
||||||
export let background
|
|
||||||
export let color
|
|
||||||
export let border
|
|
||||||
export let padding
|
|
||||||
export let hoverColor
|
|
||||||
export let hoverBackground
|
|
||||||
export let hoverBorder
|
|
||||||
export let fontFamily
|
|
||||||
|
|
||||||
export let _bb
|
export let _bb
|
||||||
let theButton
|
let theButton
|
||||||
let cssVariables
|
|
||||||
let buttonStyles
|
|
||||||
|
|
||||||
let customHoverColorClass
|
|
||||||
let customHoverBorderClass
|
|
||||||
let customHoverBackClass
|
|
||||||
|
|
||||||
let customClasses = ""
|
|
||||||
|
|
||||||
$: if (_bb.props._children && _bb.props._children.length > 0)
|
$: if (_bb.props._children && _bb.props._children.length > 0)
|
||||||
theButton && _bb.attachChildren(theButton)
|
theButton && _bb.attachChildren(theButton)
|
||||||
|
|
||||||
$: {
|
|
||||||
cssVariables = {
|
|
||||||
hoverColor,
|
|
||||||
hoverBorder,
|
|
||||||
hoverBackground,
|
|
||||||
background,
|
|
||||||
color,
|
|
||||||
border,
|
|
||||||
}
|
|
||||||
|
|
||||||
buttonStyles = buildStyle({
|
|
||||||
padding,
|
|
||||||
"font-family": fontFamily,
|
|
||||||
})
|
|
||||||
|
|
||||||
customClasses = createClasses({
|
|
||||||
hoverColor,
|
|
||||||
hoverBorder,
|
|
||||||
hoverBackground,
|
|
||||||
background,
|
|
||||||
border,
|
|
||||||
color,
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
const clickHandler = () => {
|
const clickHandler = () => {
|
||||||
_bb.call(onClick)
|
_bb.call(onClick)
|
||||||
}
|
}
|
||||||
|
@ -60,15 +17,10 @@
|
||||||
|
|
||||||
<button
|
<button
|
||||||
bind:this={theButton}
|
bind:this={theButton}
|
||||||
use:cssVars={cssVariables}
|
class={className}
|
||||||
class="{className}
|
|
||||||
{customClasses}"
|
|
||||||
disabled={disabled || false}
|
disabled={disabled || false}
|
||||||
on:click={clickHandler}
|
on:click={clickHandler}>
|
||||||
style={buttonStyles}>
|
{#if !_bb.props._children || _bb.props._children.length === 0}{text}{/if}
|
||||||
{#if !_bb.props._children || _bb.props._children.length === 0}
|
|
||||||
{contentText}
|
|
||||||
{/if}
|
|
||||||
</button>
|
</button>
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
|
|
|
@ -4,26 +4,12 @@
|
||||||
export let className = ""
|
export let className = ""
|
||||||
export let onLoad
|
export let onLoad
|
||||||
export let type = "div"
|
export let type = "div"
|
||||||
export let backgroundColor
|
|
||||||
export let color
|
|
||||||
export let borderWidth
|
|
||||||
export let borderColor
|
|
||||||
export let borderStyle
|
|
||||||
export let _bb
|
export let _bb
|
||||||
|
|
||||||
let containerElement
|
let containerElement
|
||||||
let hasLoaded
|
let hasLoaded
|
||||||
let currentChildren
|
let currentChildren
|
||||||
|
|
||||||
$: cssVariables = {
|
|
||||||
backgroundColor,
|
|
||||||
color,
|
|
||||||
borderWidth,
|
|
||||||
borderColor,
|
|
||||||
borderStyle,
|
|
||||||
}
|
|
||||||
$: classes = `${createClasses(cssVariables)} ${className}`
|
|
||||||
|
|
||||||
$: {
|
$: {
|
||||||
if (containerElement) {
|
if (containerElement) {
|
||||||
_bb.attachChildren(containerElement)
|
_bb.attachChildren(containerElement)
|
||||||
|
@ -36,87 +22,29 @@
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
{#if type === 'div'}
|
{#if type === 'div'}
|
||||||
<div
|
<div bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'header'}
|
{:else if type === 'header'}
|
||||||
<header
|
<header bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'main'}
|
{:else if type === 'main'}
|
||||||
<main
|
<main bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'footer'}
|
{:else if type === 'footer'}
|
||||||
<footer
|
<footer bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'aside'}
|
{:else if type === 'aside'}
|
||||||
<aside
|
<aside bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'summary'}
|
{:else if type === 'summary'}
|
||||||
<summary
|
<summary bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'details'}
|
{:else if type === 'details'}
|
||||||
<details
|
<details bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'article'}
|
{:else if type === 'article'}
|
||||||
<article
|
<article bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'nav'}
|
{:else if type === 'nav'}
|
||||||
<nav
|
<nav bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'mark'}
|
{:else if type === 'mark'}
|
||||||
<mark
|
<mark bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'figure'}
|
{:else if type === 'figure'}
|
||||||
<figure
|
<figure bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'figcaption'}
|
{:else if type === 'figcaption'}
|
||||||
<figcaption
|
<figcaption bind:this={containerElement} />
|
||||||
class={classes}
|
|
||||||
bind:this={containerElement}
|
|
||||||
use:cssVars={cssVariables} />
|
|
||||||
{:else if type === 'paragraph'}
|
{:else if type === 'paragraph'}
|
||||||
<p class={classes} bind:this={containerElement} use:cssVars={cssVariables} />
|
<p bind:this={containerElement} />
|
||||||
{/if}
|
{/if}
|
||||||
|
|
||||||
<style>
|
|
||||||
.backgroundColor {
|
|
||||||
background-color: var(--backgroundColor);
|
|
||||||
}
|
|
||||||
|
|
||||||
.color {
|
|
||||||
color: var(--color);
|
|
||||||
}
|
|
||||||
|
|
||||||
.borderColor {
|
|
||||||
border-color: var(--borderColor);
|
|
||||||
}
|
|
||||||
|
|
||||||
.borderWidth {
|
|
||||||
border-width: var(--borderWidth);
|
|
||||||
}
|
|
||||||
|
|
||||||
.borderStyle {
|
|
||||||
border-style: var(--borderStyle);
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
|
|
|
@ -2,28 +2,25 @@
|
||||||
import { buildStyle } from "./buildStyle.js"
|
import { buildStyle } from "./buildStyle.js"
|
||||||
export let className = ""
|
export let className = ""
|
||||||
export let type
|
export let type
|
||||||
export let _bb
|
|
||||||
export let text = ""
|
export let text = ""
|
||||||
export let fontFamily = ""
|
|
||||||
export let color = ""
|
export let _bb
|
||||||
|
|
||||||
let containerElement
|
let containerElement
|
||||||
|
|
||||||
$: containerElement && !text && _bb.attachChildren(containerElement)
|
$: containerElement && !text && _bb.attachChildren(containerElement)
|
||||||
$: style = buildStyle({ "font-family": fontFamily, color })
|
|
||||||
// $: console.log("HEADING", color)
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
{#if type === 'h1'}
|
{#if type === 'h1'}
|
||||||
<h1 class={className} {style} bind:this={containerElement}>{text}</h1>
|
<h1 class={className} bind:this={containerElement}>{text}</h1>
|
||||||
{:else if type === 'h2'}
|
{:else if type === 'h2'}
|
||||||
<h2 class={className} {style} bind:this={containerElement}>{text}</h2>
|
<h2 class={className} bind:this={containerElement}>{text}</h2>
|
||||||
{:else if type === 'h3'}
|
{:else if type === 'h3'}
|
||||||
<h3 class={className} {style} bind:this={containerElement}>{text}</h3>
|
<h3 class={className} bind:this={containerElement}>{text}</h3>
|
||||||
{:else if type === 'h4'}
|
{:else if type === 'h4'}
|
||||||
<h4 class={className} {style} bind:this={containerElement}>{text}</h4>
|
<h4 class={className} bind:this={containerElement}>{text}</h4>
|
||||||
{:else if type === 'h5'}
|
{:else if type === 'h5'}
|
||||||
<h5 class={className} {style} bind:this={containerElement}>{text}</h5>
|
<h5 class={className} bind:this={containerElement}>{text}</h5>
|
||||||
{:else if type === 'h6'}
|
{:else if type === 'h6'}
|
||||||
<h6 class={className} {style} bind:this={containerElement}>{text}</h6>
|
<h6 class={className} bind:this={containerElement}>{text}</h6>
|
||||||
{/if}
|
{/if}
|
||||||
|
|
|
@ -4,11 +4,6 @@
|
||||||
export let url = ""
|
export let url = ""
|
||||||
export let text = ""
|
export let text = ""
|
||||||
export let openInNewTab = false
|
export let openInNewTab = false
|
||||||
export let color
|
|
||||||
export let hoverColor
|
|
||||||
export let underline = false
|
|
||||||
export let fontFamily
|
|
||||||
export let fontSize
|
|
||||||
|
|
||||||
export let _bb
|
export let _bb
|
||||||
|
|
||||||
|
@ -16,43 +11,12 @@
|
||||||
|
|
||||||
$: anchorElement && !text && _bb.attachChildren(anchorElement)
|
$: anchorElement && !text && _bb.attachChildren(anchorElement)
|
||||||
$: target = openInNewTab ? "_blank" : "_self"
|
$: target = openInNewTab ? "_blank" : "_self"
|
||||||
$: cssVariables = {
|
|
||||||
hoverColor,
|
|
||||||
color,
|
|
||||||
textDecoration: underline ? "underline" : "none",
|
|
||||||
fontSize,
|
|
||||||
fontFamily,
|
|
||||||
}
|
|
||||||
$: classes = createClasses(cssVariables)
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<a
|
<a href={url} bind:this={anchorElement} {target}>{text}</a>
|
||||||
href={url}
|
|
||||||
bind:this={anchorElement}
|
|
||||||
class={classes}
|
|
||||||
{target}
|
|
||||||
use:cssVars={cssVariables}>
|
|
||||||
{text}
|
|
||||||
</a>
|
|
||||||
|
|
||||||
<style>
|
<style>
|
||||||
.color {
|
|
||||||
color: var(--color);
|
|
||||||
}
|
|
||||||
|
|
||||||
.hoverColor:hover {
|
|
||||||
color: var(--color);
|
|
||||||
}
|
|
||||||
|
|
||||||
.textDecoration {
|
.textDecoration {
|
||||||
text-decoration: var(--textDecoration);
|
text-decoration: var(--textDecoration);
|
||||||
}
|
}
|
||||||
|
|
||||||
.fontSize {
|
|
||||||
font-size: var(--fontSize);
|
|
||||||
}
|
|
||||||
|
|
||||||
.fontFamily {
|
|
||||||
font-family: var(--fontFamily);
|
|
||||||
}
|
|
||||||
</style>
|
</style>
|
||||||
|
|
|
@ -4,45 +4,35 @@
|
||||||
export let text = ""
|
export let text = ""
|
||||||
export let className = ""
|
export let className = ""
|
||||||
|
|
||||||
export let formattingTag = ""
|
export let type = ""
|
||||||
|
|
||||||
export let fontFamily = ""
|
|
||||||
export let fontSize = "1em"
|
|
||||||
export let textAlign = ""
|
|
||||||
export let verticalAlign = ""
|
|
||||||
export let color = ""
|
|
||||||
|
|
||||||
export let _bb
|
export let _bb
|
||||||
|
|
||||||
const isTag = tag => (formattingTag || "").indexOf(tag) > -1
|
const isTag = tag => type === tag
|
||||||
|
|
||||||
$: style = buildStyle({
|
|
||||||
"font-size": fontSize,
|
|
||||||
"font-family": fontFamily,
|
|
||||||
color,
|
|
||||||
})
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
{#if isTag('none')}
|
{#if isTag('none')}
|
||||||
<span {style}>{text}</span>
|
<span>{text}</span>
|
||||||
{:else if isTag('<b>')}
|
{:else if isTag('bold')}
|
||||||
<b class={className} {style}>{text}</b>
|
<b class={className}>{text}</b>
|
||||||
{:else if isTag('<strong>')}
|
{:else if isTag('strong')}
|
||||||
<strong class={className} {style}>{text}</strong>
|
<strong class={className}>{text}</strong>
|
||||||
{:else if isTag('<i>')}
|
{:else if isTag('italic')}
|
||||||
<i class={className} {style}>{text}</i>
|
<i class={className}>{text}</i>
|
||||||
{:else if isTag('<em>')}
|
{:else if isTag('emphasis')}
|
||||||
<em class={className} {style}>{text}</em>
|
<em class={className}>{text}</em>
|
||||||
{:else if isTag('<mark>')}
|
{:else if isTag('mark')}
|
||||||
<mark class={className} {style}>{text}</mark>
|
<mark class={className}>{text}</mark>
|
||||||
{:else if isTag('<small>')}
|
{:else if isTag('small')}
|
||||||
<small class={className} {style}>{text}</small>
|
<small class={className}>{text}</small>
|
||||||
{:else if isTag('<del>')}
|
{:else if isTag('del')}
|
||||||
<del class={className} {style}>{text}</del>
|
<del class={className}>{text}</del>
|
||||||
{:else if isTag('<ins>')}
|
{:else if isTag('ins')}
|
||||||
<ins class={className} {style}>{text}</ins>
|
<ins class={className}>{text}</ins>
|
||||||
{:else if isTag('<sub>')}
|
{:else if isTag('sub')}
|
||||||
<sub class={className} {style}>{text}</sub>
|
<sub class={className}>{text}</sub>
|
||||||
{:else if isTag('<sup>')}
|
{:else if isTag('sup')}
|
||||||
<sup class={className} {style}>{text}</sup>
|
<sup class={className}>{text}</sup>
|
||||||
{:else}{text}{/if}
|
{:else}
|
||||||
|
<span>{text}</span>
|
||||||
|
{/if}
|
||||||
|
|