Svelte 是构建 Web 应用程序的一种新框架。Svelte 是一个编译器,它将声明性组件转换成高效的 JavaScript 代码,并快速响应细粒度地更新 DOM。
最近一直在学习前端新框架Svelte。号称比vue还快,无虚拟dom操作。 今天就给大家分享一些svelte自定义组件的相关知识。
在lib公共目录下新建headerbar和tabbar组件。 在需要使用组件的页面或者公共模板__layout.svelte中引入组件。
import HeaderBar from '$lib/HeaderBar.svelte';
import TabBar from '$lib/TabBar.svelte';
svelte自定义导航条headerbar组件
在vue中通过props来定义组件属性,而在svelte则是通过export导出自定义属性。
<!--
<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)
}
</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>
支持 自定义背景(渐变色)、文字颜色、标题居中、搜索框、沉浸式悬浮、是否固定及层叠 等功能。 另外还支持 自定义插槽 丰富组件功能,实现一些地址选择、圆点提示、图片等功能。
<HeaderBar back="false" bgcolor="linear-gradient(to right, #36f4da, #f889ff)" color="#fff">
<svelte:fragment slot="title">上海 <i class="iconfont icon-arrD"></i></svelte:fragment>
<svelte:fragment slot="search">
<div class="seach-box flex-c flex1">
<input class="ipt flex1" placeholder="Search..." />
</div>
</svelte:fragment>
<svelte:fragment slot="right">
<div class="btn"><i class="iconfont icon-weizhi"></i></div>
<div class="btn"><img src="img/logo.png" height="12" alt="" /></div>
</svelte:fragment>
</HeaderBar>
svelte自定义tabbar组件
<script>
export let current = 0
export let color = '#999'
export let bgcolor = '#fff'
export let activeColor = '#ff3e00'
export let fixed = false
export let tabs = [
{
path: '/',
icon: 'icon-face',
title: '消息',
badge: 18,
},
{
path: '/contact',
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>
支持自定义背景(渐变背景)、文字颜色|选中颜色、是否固定、中间按钮dock凸起等功能。
<script>
function handleTabbar(e) {
console.log('tabbar索引值:' + e.detail)
}
</script>
<TabBar bgcolor="#ffc107" color="#fff" activeColor="#fb4e30" on:click={handleTabbar}
tabs={
[
{
icon: 'icon-face',
title: 'Face',
dot: true,
iconSize: '24px'
},
{
img: 'https://gw.alicdn.com/tfs/TB1CoEwVrvpK1RjSZFqXXcXUVXa-185-144.png',
title: '咸鱼',
dock: true,
dockBg: '#f00',
iconSize: '30px',
},
{
path: '/me',
icon: 'icon-female',
title: '我',
},
]
}
/>
注意
vue通过this.$emit来向父组件传递事件。而在svelte中则是通过createEventDispatcher来处理事件传递。
import { createEventDispatcher } from 'svelte'
const dispatch = createEventDispatcher()
dispatch('click', ...)
svelte获取页面路由地址
import { page } from '$app/stores'
svelte函数跳转页面
import { goto } from '$app/navigation'
好了,svelte自定义组件就分享到这里。后面还会分享一个svelte自定义弹窗组件。
|