Been learning about Svelte recently. The current version has reached svelte3.x.
Today I will share with you two commonly used custom components Navbar+Tabbar.

svelte official website: https://svelte.dev/

Create new Headerbar and Tabbar components in the public lib directory.

image.png

introduces component

import HeaderBar from '$lib/HeaderBar.svelte';
import TabBar from '$lib/TabBar.svelte';

Svelte custom navbar Navbar

<!-- //自定义HeaderBar组件 -->
<script>
    // 是否显示回退按钮
    export let back = true
    // 标题
    export let title = ''
    // 颜色
    export let color = '#fff'
    // 背景色
    export let bgcolor = '#22d59c'
    // 是否居中标题
    export let center = false
    // 是否固定
    export let fixed = false
    // 是否镂空透明
    export let transparent = false
    // 层级
    export let zIndex = 2021

    function goBack() {
        console.log('go back')
        history.go(-1)
        // history.back(-1)
    }
</script>

<div class="header-bar" class:transparent class:fixed={transparent||fixed}>
    <div class="header-bar__wrap flexbox flex-alignc" style:color style:background={bgcolor} style:z-index={zIndex}>
        <!-- //返回 -->
        {#if back && back != 'false'}
            <div class="action hdbar-action__left" on:click={goBack}>
                <slot name="backIco" /><slot name="backText" />
            </div>
        {/if}

        <!-- //标题 -->
        <div class="hdbar-title" class:center>
            {#if $$slots.title}
                <slot name="title" />
            {:else}
                {@html title}
            {/if}
        </div>

        <!-- //搜索框 -->
        <div class="action hdbar-action__search">
            <slot name="search" />
        </div>

        <!-- //右侧 -->
        <div class="action hdbar-action__right">
            <slot name="right" />
        </div>
    </div>
</div>

image.png

as shown above : The navigation bar supports custom background (gradient color), text color, title centering, search box, immersive suspension, whether it is fixed or not, and cascading functions.
It also supports custom slot rich component functions to achieve some address selection, dot prompts, pictures and other functions.

Quickly call components as follows.

<HeaderBar bgcolor="#607d8b" color="#fff" title="Svelte自定义导航" center zIndex="6666">
<HeaderBar back="true" bgcolor="linear-gradient(to right, #4978ff, #17f532)" color="#e4ff00">
    <svelte:fragment slot="backIco"><i class="iconfont icon-close"></i></svelte:fragment>
    <svelte:fragment slot="search">
        <div class="flex-c flex1">
            <input class="ipt flex1" placeholder="Search..." value="搜索关键字..." />
        </div>
    </svelte:fragment>
    <svelte:fragment slot="right">
        <div class="ml-20"><i class="iconfont icon-shoucang"></i></div>
        <div class="ml-20"><i class="iconfont icon-female"></i></div>
        <!-- <div class="ml-20"><img src="img/logo.png" height="12" /></div> -->
    </svelte:fragment>
</HeaderBar>

Svelte custom menu bar Tabbar

image.png

/**
 * @Desc     Svelte自定义Tabbar组件
 * @Time     andy by 2022/3/12
 * @About    Q:282310962  wx:xy190310
 */
<script>
    // tab默认索引
    export let current = 0
    // 文字颜色
    export let color = '#999'
    // 背景色
    export let bgcolor = '#fff'
    // 激活颜色
    export let activeColor = '#ff3e00'
    // 是否固定
    export let fixed = false
    // tab选项
    export let tabs = [
        {
            path: '/',
            icon: 'icon-face',
            title: '消息',
            badge: 18,
        },
        {
            path: '/contact',
            // icon: 'icon-choose',
            img: 'https://img.yzcdn.cn/vant/user-inactive.png',
            activeImg: 'https://img.yzcdn.cn/vant/user-active.png',
            title: '联系人',
        },
        {
            path: '/me',
            icon: 'icon-female',
            title: '我',
            dot: true,
        }
    ]

    import { page } from '$app/stores'
    import { goto } from '$app/navigation'
    import { onMount, createEventDispatcher } from 'svelte'
    const dispatch = createEventDispatcher()

    $: currentTabIndex = current

    onMount(() => {
        console.log('路由:', $page)
        console.log('路由地址:', $page.url)
        const curPath = $page.url.pathname
        tabs.map((item, index) => {
            if(item.path == curPath) {
                currentTabIndex = index
            }
        })
    })

    function changeTabs(index, item) {
        currentTabIndex = index
        dispatch('click', index)
        if(item.path) {
            goto(item.path)
        }
    }
</script>

<div class="tab-bar" class:fixed>
    <div class="tab-bar__wrap flexbox flex-alignc" style="background: {bgcolor}">
        {#each tabs as item,i}
            <div class="navigator" class:on={currentTabIndex==i} on:click={changeTabs(i, item)}>
                <div class="ico" class:dock={item.dock}>
                    {#if item.dock}<i class="dock-bg" style:background={item.dockBg ? item.dockBg : activeColor}></i>{/if}
                    {#if item.icon}<i class={'iconfont '+item.icon} style:color={currentTabIndex == i && !item.dock ? activeColor : color} style:font-size={item.iconSize}></i>{/if}
                    {#if item.img}<img class="iconimg" src={currentTabIndex == i && !item.dock ? item.activeImg : item.img} style:font-size={item.iconSize} />{/if}
                    {#if item.badge}<em class="vui__badge">{@html item.badge}</em>{/if}
                    {#if item.dot}<em class="vui__badge-dot"></em>{/if}
                </div>
                <div class="txt" style:color={currentTabIndex == i ? activeColor : color}>{@html item.title}</div>
            </div>
        {/each}
    </div>
</div>

Tabbar.svelte supports custom background (gradient background), text color | selected color, fixed or not, center button dock raised and other functions.

It should be noted that the event trigger needs to be introduced from the svelte child component to pass the event to the parent component.

import { createEventDispatcher } from 'svelte'
const dispatch = createEventDispatcher()
dispatch('click', 999)

After a while, I found that the svelte development component is indeed a lot simpler than vue. Unfortunately, there is no way to introduce components globally. If you have some better methods, please leave a message to exchange.


xiaoyan2017
765 声望318 粉丝

web前端开发爱好者,专注于前端h5、jquery、vue、react、angular等技术研发实战项目案例。


引用和评论

0 条评论