1.0.1 • Published 12 days ago

@tanglemedia/svelte-starter-layout v1.0.1

Weekly downloads
-
License
MIT
Repository
-
Last release
12 days ago

@tanglemedia/svelte-starter-layout

The Layout package is responsible for the main layout of your app after the user is authorized, but it also contains components responsible for style settings adn functionalities.

Most of the componet from the Layout packages behave as wrappers, that is, are components that have on them so you can pass it what you actually want the component to display, and it will display that in a nicely way.

Some of the componets present on the Layout package are also present on SkeletonUI package, and if you want more in depth analisys of those components you can check it out at their documentation. Those components are AppBar, AppRail, AppRailAnchor, AppRailTile, AppShell, TabGroup, TabAnchor. All these components are present in the Layout package, but they behave the same way as the ones in SkeletonUI.

Demo

On this section we are going to display how you can use some of the components that the Layout package provides on your svelte app.

LayoutSettings

The LayoutSettings is responsible to read some configurations of your app.yml config file, like:

  • app.viewport
  • app.seo.title
  • app.settings.background.primary_color
  • app.settings.background.secondary_color
  • app.settings.text.primary_color
  • app.settings.text.secondary_color After it gets the values of all those configurations it runs a function that calculates your project colors and set in your localStorage the colors:
localStorage.setItem('--settings-primary-color', primaryColor);
localStorage.setItem('--settings-secondary-color', secondaryColor);
localStorage.setItem('--settings-text-primary-color', textPrimaryColor);
localStorage.setItem('--settings-text-secondary-color', textSecondaryColor);
localStorage.setItem('--settings-text-contrast-primary-color', textContrastPrimary);
localStorage.setItem('--settings-text-contrast-secondary-color', textContrastSecondary);
customStyles = `--settings-primary-color: ${primaryColor}; --settings-secondary-color: ${secondaryColor}; 
--settings-text-primary-color: ${textPrimaryColor}; --settings-text-secondary-color: ${textSecondaryColor};
--settings-text-contrast-primary-color: ${textContrastPrimary}; --settings-text-contrast-secondary-color: ${textContrastSecondary}`;

And this is how you would use it, it would be in your first layout of your app.

<script lang='ts'>
	import '$lib/styles/main.css';
	import { ConfigProvider } from '@tanglemedia/svelte-starter-core';
	import { QueryClientProvider } from '@tanstack/svelte-query';
	import { Toaster } from 'svelte-french-toast';
	import { LayoutSettings } from '@tanglemedia/svelte-starter-layout';
</script>

<Toaster />
<QueryClientProvider >
	<ConfigProvider configFactory={provideConfig()}>
		<LayoutSettings>
			<slot />
		</LayoutSettings>
	</ConfigProvider>
</QueryClientProvider>

AppLayout

This is the AppLayout component from the @tanglemedia/svelte-starter-layout package, The AppLayout component is probably one of the most complex components in the @tanglemedia libraries.

Its main goal is to display a layout that will be followed on your entire (app) group route. It can change from a basic layout to a mobile layout if you pass the right props, but in all layouts, it has a place to display what page you are, a navigation place, and a slot place for you to actually display the content of a certain page.

<AppLayout sidebarExtraClass="pt-5" footerExtraClass="h-12 variant-filled-primary" subNavBarPageDescription={subnavbarDescription} subNavBar={true} backUrl={() => {goSomeWhereBack()}} subNavBarBackgroundImage={backgroundImage} display={"mobile"} appLogoImage={logo} headerImageClass={`w-24 ${sidebarCropped ? 'mt-2 md:w-20 md:mx-0' : 'md:w-32 md:mx-10'}`} on:sidebar={(e) => {sidebarCropped = e.detail;}}>
    <UserAppButton {userAvatar} userEmail={user?.email} userName={`${user?.first_name} ${user?.last_name}`} profileLink={'/profile'} slot="userAppButton" buttonIconClasses={'text-black'} onSuccess={async () => {
    await logout();
    }}/>
    <div slot="content" class="xl:mt-3 px-5 md:px-0">
    <PageTransition url={data.url}>
        <slot />
    </PageTransition>
    </div>
</AppLayout>

Breaking Changes

Migrating from 0.0.24 to 1.0.0

On this update we redesigned completely the way you add the component yo your +layout.svelte page, we now have three new components:

  1. AppHeader
  2. AppSidebar
  3. AppFooter

As well as new stores:

  1. subNavbarStore
  2. breadcrumbStore
  3. drawerStore
  4. sidebarStore

First let's talk about the redesign of the layout.yml file as well. This is how the new layout.yml file should look like:

display:
  # We now only have TWO display modes: mobile, and desktop.
  mode: mobile

# We also separated the settings into GLOBAL, MOBILE, and DESKTOP. Although still most of the configuration are global
# Global settings
header:
  #enabled is a new value, and it is used on the new AppLayout component, to either display the header or not.
  enabled: true
  # These settings are NOT inside a display object anymore.
  profileButton: true
  subNavbar: true
  logoHref: '/dashboard'
  userProfile:
    links:
      - name: Profile
        href: /profile
      - name: Change Password
        href: /profile?tab=change_password

sidebar:
  #enabled is a new value, and it is used on the new AppLayout component, to either display the sidebar or not.
  enabled: true
  # These settings are NOT inside a display object anymore.
  position: left
  offCanvas: true

  # These configurations are untouched, but many people asked why they are empty (bottom, and buttons).
  # They are empty because they are automatically set with the primary and secondary colours when you set the LayoutSettings components, so these are more like OVERWRITES for you primary and secondary colours of you sidebar menu.
  bottom:
    backgroundColor:
    activeBackgroundColor:
    iconColor:
    iconActiveColor:

  buttons:
    mode: horizontal
    backgroundColor:
    activeBackgroundColor:
    textColor:
    activeTextColor:

# Mobile specific settings
# Because the footer section is only visible on mobile display modes, then the settings for the footer are inside the mobile object.
mobile:
  footer:
    #enabled is a new value, and it is used on the new AppLayout component, to either display the footer or not.
    enabled: true
    showTitle: false

desktop:

Now that you know about the updates on the layout.yml file, let's take a look at the changes on the way you set you layout.

Previously you would set the layout like this:

  <AppLayout sidebarExtraClass="pt-5" footerExtraClass="h-12 variant-filled-primary" subNavBarPageDescription={subnavbarDescription} subNavBar={true} backUrl={() => {goSomeWhereBack()}} subNavBarBackgroundImage={backgroundImage} display={"mobile"} appLogoImage={logo} headerImageClass={`w-24 ${sidebarCropped ? 'mt-2 md:w-20 md:mx-0' : 'md:w-32 md:mx-10'}`} on:sidebar={(e) => {sidebarCropped = e.detail;}}>
    <UserAppButton {userAvatar} userEmail={user?.email} userName={`${user?.first_name} ${user?.last_name}`} profileLink={'/profile'} slot="userAppButton" buttonIconClasses={'text-black'} onSuccess={async () => {
      await logout();
    }}/>
    <div slot="content" class="xl:mt-3 px-5 md:px-0">
      <PageTransition url={data.url}>
        <slot />
      </PageTransition>
    </div>
  </AppLayout>

Now you could set it like this:

<AppLayout>
  <AppHeader
    slot="header"
    subNavbarBackgroundImage={backgroundImage}
    {logo}
    logoClass="md:h-10"
    autoSetBreadcrumbs={false}
  >
    <UserAppButton
      slot="userAppButton"
      {avatar}
      email={user?.email}
      name={`${user?.first_name} ${user?.last_name}`}
      profileLink={'/profile'}
      iconHexColor="#fff"
      buttonIconClasses={'text-white'}
      onSuccess={async () => {
        await logout();
      }}
    />
  </AppHeader>
  <AppSidebar slot="sidebar" />
  <AppFooter slot="footer" />
  <div>
    <slot />
  </div>
</AppLayout>

The new way we break down the AppLayout into other components, to make it easier to understand what each component does, as well as make the logic behind the components way easier, and last but not the least it makes the naming of variables easier and less confusing like it was on the previous version where everything was in one component.

Finally let's take a look at the new stores:

  1. SubnavbarStore: This store makes you able to manually set the value of the subnavbar title, and description. Keep in mind that the subnavbar title is automatically assigned, but you can overwrite it with this store, the description of the will not automatically be assigned, so the only way is through the store.
<script lang="ts">
	import {
		getSubNavbarStore,
		type SubNavbarSettings,
	} from '@tanglemedia/svelte-starter-layout';
	import { onDestroy } from 'svelte';

	const subNavbarStore = getSubNavbarStore();
	const subNavbar: SubNavbarSettings = {
		value: {
			title: 'Add single item',
      description: 'Page to add single item'
		}
	};

	$: subNavbarStore.set(subNavbar);

	onDestroy(() => {
		subNavbarStore.clear();
	});
</script>
  1. BreadcrumbStore: This store makes you able to manually set the value of the breadcrumb items. Keep in mind that the breadcrumb items are automatically assigned, but you can overwrite it with this store.
<script lang="ts">
	import {
		getBreadcrumbStore,
		type BreadcrumbSettings
	} from '@tanglemedia/svelte-starter-layout';
	import { onDestroy } from 'svelte';

	const breadcrumbStore = getBreadcrumbStore();
	const breadcrumb: BreadcrumbSettings = {
		value: [
			{
				title: 'Dashboard',
				url: '/dashboard'
			},
			{
				title: 'Add',
				url: '/dashboard/add'
			},
			{
				title: 'Item',
				url: '/dashboard/add/1'
			}
		]
	};
	$: breadcrumbStore.set(breadcrumb);

	onDestroy(() => {
		breadcrumbStore.clear();
	});
</script>
  1. sidebarStore: This store makes you able to manually set the value of the sidebar, to either show as cropped or not cropped. Keep in mind that the sidebar cropped or not are internal functions already, but if you want to set cropped as default, you could do it through this store.
<script lang="ts">
	import {
		getSidebarStore,
		type SidebarSettings
	} from '@tanglemedia/svelte-starter-layout';
	import { onDestroy } from 'svelte';

	const sidebarStore = getSidebarStore();
	const sidebar: SidebarSettings = {
    // open or closed
		value: 'open'
	};

  sidebarStore.set(sidebar);
</script>

For mode demos and to check out all the components, please visit our storybook website

1.0.1

12 days ago

1.0.0

2 months ago

0.0.24

3 months ago

0.0.23

3 months ago

0.0.22

3 months ago

0.0.21

3 months ago

0.0.20

4 months ago

0.0.19

4 months ago

0.0.17

4 months ago

0.0.18

4 months ago

0.0.16

4 months ago

0.0.15

4 months ago

0.0.14

4 months ago

0.0.10

5 months ago

0.0.11

5 months ago

0.0.12

5 months ago

0.0.13

5 months ago

0.0.9

5 months ago

0.0.8

5 months ago

0.0.5

5 months ago

0.0.7

5 months ago

0.0.6

5 months ago

0.0.0

5 months ago

0.0.3

5 months ago

0.0.2

5 months ago

0.0.4

5 months ago

0.0.1

6 months ago