forked from tsai/budibase
34 changed files with 292 additions and 168 deletions
@ -0,0 +1,57 @@ |
|||
<script> |
|||
import ComponentSelectionList from "./ComponentSelectionList.svelte" |
|||
import DevicePreviewSelect from "./DevicePreviewSelect.svelte" |
|||
import ThemeEditor from "./ThemeEditor.svelte" |
|||
import AppThemeSelect from "./AppThemeSelect.svelte" |
|||
import AppPreview from "./AppPreview.svelte" |
|||
import { store } from "builderStore" |
|||
</script> |
|||
|
|||
<div class="app-panel"> |
|||
<div class="header"> |
|||
<ComponentSelectionList /> |
|||
{#if $store.clientFeatures.devicePreview} |
|||
<DevicePreviewSelect /> |
|||
{/if} |
|||
{#if $store.clientFeatures.customThemes} |
|||
<ThemeEditor /> |
|||
{:else if $store.clientFeatures.spectrumThemes} |
|||
<AppThemeSelect /> |
|||
{/if} |
|||
</div> |
|||
<div class="content"> |
|||
{#key $store.version} |
|||
<AppPreview /> |
|||
{/key} |
|||
</div> |
|||
</div> |
|||
|
|||
<style> |
|||
.app-panel { |
|||
flex: 1 1 auto; |
|||
overflow-y: auto; |
|||
display: flex; |
|||
flex-direction: column; |
|||
justify-content: flex-start; |
|||
align-items: stretch; |
|||
gap: var(--spacing-m); |
|||
padding: var(--spacing-l) 24px; |
|||
} |
|||
.header { |
|||
display: flex; |
|||
flex-direction: row; |
|||
justify-content: flex-start; |
|||
align-items: flex-start; |
|||
gap: 1rem; |
|||
margin-left: -6px; |
|||
} |
|||
.header > :global(*) { |
|||
flex: 0 0 auto; |
|||
} |
|||
.header > :global(*:first-child) { |
|||
flex: 1 1 auto; |
|||
} |
|||
.content { |
|||
flex: 1 1 auto; |
|||
} |
|||
</style> |
|||
@ -1 +0,0 @@ |
|||
export { default } from "./CurrentItemPreview.svelte" |
|||
@ -0,0 +1,70 @@ |
|||
<script> |
|||
import { Icon, Heading } from "@budibase/bbui" |
|||
|
|||
export let title |
|||
export let showAddButton |
|||
export let onClickAddButton |
|||
</script> |
|||
|
|||
<div class="navigation-panel"> |
|||
<div class="header"> |
|||
<div class="title"> |
|||
<Heading size="XS">{title || ""}</Heading> |
|||
</div> |
|||
{#if showAddButton} |
|||
<div class="add-button"> |
|||
<Icon name="Add" on:click={onClickAddButton} /> |
|||
</div> |
|||
{/if} |
|||
</div> |
|||
<slot /> |
|||
</div> |
|||
|
|||
<style> |
|||
.navigation-panel { |
|||
width: 260px; |
|||
background: var(--background); |
|||
border-right: var(--border-light); |
|||
display: flex; |
|||
flex-direction: column; |
|||
justify-content: flex-start; |
|||
align-items: stretch; |
|||
} |
|||
.header { |
|||
display: flex; |
|||
flex-direction: row; |
|||
justify-content: space-between; |
|||
align-items: center; |
|||
padding: var(--spacing-m) var(--spacing-l); |
|||
border-bottom: var(--border-light); |
|||
gap: var(--spacing-l); |
|||
} |
|||
.title { |
|||
flex: 1 1 auto; |
|||
width: 0; |
|||
} |
|||
.title :global(h1) { |
|||
overflow: hidden; |
|||
font-weight: 600; |
|||
text-overflow: ellipsis; |
|||
white-space: nowrap; |
|||
} |
|||
.add-button { |
|||
flex: 0 0 32px; |
|||
height: 32px; |
|||
display: grid; |
|||
place-items: center; |
|||
border-radius: 4px; |
|||
position: relative; |
|||
cursor: pointer; |
|||
background: var(--spectrum-semantic-cta-color-background-default); |
|||
transition: background var(--spectrum-global-animation-duration-100, 130ms) |
|||
ease-out; |
|||
} |
|||
.add-button:hover { |
|||
background: var(--spectrum-semantic-cta-color-background-hover); |
|||
} |
|||
.add-button :global(svg) { |
|||
fill: white; |
|||
} |
|||
</style> |
|||
@ -0,0 +1 @@ |
|||
Components |
|||
@ -0,0 +1,5 @@ |
|||
<script> |
|||
import { redirect } from "@roxi/routify" |
|||
|
|||
$redirect(`./screens`) |
|||
</script> |
|||
@ -0,0 +1 @@ |
|||
Layouts |
|||
@ -0,0 +1 @@ |
|||
Navigation |
|||
@ -0,0 +1 @@ |
|||
<slot /> |
|||
@ -0,0 +1,69 @@ |
|||
<script> |
|||
import { Search, Layout, Select } from "@budibase/bbui" |
|||
import NavigationPanel from "components/design/NavigationPanel/NavigationPanel.svelte" |
|||
import { roles } from "stores/backend" |
|||
import { store, allScreens } from "builderStore" |
|||
import NavItem from "components/common/NavItem.svelte" |
|||
import ScreenDropdownMenu from "./_components/ScreenDropdownMenu.svelte" |
|||
import AppPanel from "components/design/AppPanel/AppPanel.svelte" |
|||
import { RoleColours } from "constants" |
|||
|
|||
let searchString |
|||
let accessRole |
|||
|
|||
$: filteredScreens = getFilteredScreens($allScreens, searchString) |
|||
|
|||
const getFilteredScreens = (screens, searchString) => { |
|||
return screens |
|||
.filter( |
|||
screen => !searchString || screen.routing.route.includes(searchString) |
|||
) |
|||
.slice() |
|||
.sort((a, b) => { |
|||
return a.routing.route < b.routing.route ? -1 : 1 |
|||
}) |
|||
} |
|||
|
|||
const getRoleColor = roleId => { |
|||
return RoleColours[roleId] || "pink" |
|||
} |
|||
</script> |
|||
|
|||
<NavigationPanel title="Screens" showAddButton onClickAddButton> |
|||
<Layout paddingX="L" paddingY="XL" gap="S"> |
|||
<Search |
|||
placeholder="Enter a route to search" |
|||
value={searchString} |
|||
on:change={e => (searchString = e.detail)} |
|||
/> |
|||
<Select |
|||
bind:value={accessRole} |
|||
placeholder="All screens" |
|||
getOptionLabel={role => role.name} |
|||
getOptionValue={role => role._id} |
|||
options={$roles} |
|||
/> |
|||
</Layout> |
|||
{#each filteredScreens as screen (screen._id)} |
|||
<NavItem |
|||
icon={screen.routing.route === "/" ? "Home" : "WebPage"} |
|||
indentLevel={0} |
|||
selected={$store.selectedScreenId === screen._id} |
|||
text={screen.routing.route} |
|||
on:click={() => ($store.selectedScreenId = screen._id)} |
|||
color={getRoleColor(screen.routing.roleId)} |
|||
> |
|||
<ScreenDropdownMenu screenId={screen._id} /> |
|||
</NavItem> |
|||
<!--{#if selectedScreen?._id === screen.id}--> |
|||
<!-- <ComponentTree--> |
|||
<!-- level={1}--> |
|||
<!-- components={selectedScreen.props._children}--> |
|||
<!-- currentComponent={$selectedComponent}--> |
|||
<!-- {dragDropStore}--> |
|||
<!-- />--> |
|||
<!--{/if}--> |
|||
{/each} |
|||
</NavigationPanel> |
|||
|
|||
<AppPanel /> |
|||
@ -0,0 +1 @@ |
|||
Theme |
|||
@ -1,2 +0,0 @@ |
|||
<!-- routify:options index=1 --> |
|||
<slot /> |
|||
@ -1,6 +0,0 @@ |
|||
<script> |
|||
import { goto } from "@roxi/routify" |
|||
import { FrontendTypes } from "constants" |
|||
|
|||
$goto(`./${FrontendTypes.SCREEN}`) |
|||
</script> |
|||
@ -1,6 +1,19 @@ |
|||
<script> |
|||
import { goto } from "@roxi/routify" |
|||
import { DesignTabs } from "constants" |
|||
import { allScreens } from "builderStore" |
|||
import { onMount } from "svelte" |
|||
import { redirect } from "@roxi/routify" |
|||
|
|||
$goto(`./${DesignTabs.SCREENS}`) |
|||
let loaded = false |
|||
|
|||
onMount(() => { |
|||
if ($allScreens?.length) { |
|||
$redirect(`./${$allScreens[0]._id}`) |
|||
} else { |
|||
loaded = true |
|||
} |
|||
}) |
|||
</script> |
|||
|
|||
{#if loaded} |
|||
You need to create a screen! |
|||
{/if} |
|||
|
|||
Loading…
Reference in new issue