Vue造轮子系列-Button组件

时间:2021-1-8 作者:admin

1、前言

学习并使用Vue有一段时间了,并且使用过Element UIiviewant-designUI框架,然后就想着自己也做一套自己的UI框架,也算是对自己这么久学习Vue框架的一个总结。在写该组件库的时候,也踩过很多坑,碰到过一些以前使用Vue未曾碰到的问题,因此,这一系列的文章主要是记录下自己在造轮子过程中遇到的问题及思路。之后的每篇文章都会按照需求,实现,遇到的问题这三个角度来写,今天就先以Button组件开始吧。

2、Button组件-需求

在我使用过其他框架来看,按钮主要有以下几个方面的需求:

  • 可点击/不可点击
  • 按钮的类型type
  • 按钮的大小size
  • loading状态
  • icon图标(位置)
  • hover状态
  • 按下按钮的状态

以上就是我在做Button组件时想到的几个点,当然没有考虑的很全面,但是能满足基本的使用。

3、Button组件-实现

首先想一下用户使用组件的API,大概就是如下进行调用:

<y-button>点我</y-button>
<y-button type="xxx">点我</y-button>
<y-button size="xxx">点我</y-button>
<y-button icon="xxx">点我</y-button>
<y-button disabled>点我</y-button>
<y-button loading>点我</y-button>

知道用户怎么使用按钮之后,接下来就是代码实现了。Button组件的实现还是相对于比较容易的,主要是一些css样式的编写,js部分的话主要是对事件的处理。

好了,话不多说,直接上代码:

<button
    class="y-button"
    :class="classes"
    @click="onClick"
    :disabled="disabled"
  >
    <y-icon class="icon" v-if="icon && !loading" :name="icon"></y-icon>
    <y-icon class="loading icon" v-if="loading" name="loading"></y-icon>
    <div class="content">
      <slot></slot>
    </div>
  </button>

接收的参数如下:

props: {
    icon: {
      type: String,
      default: '',
    },
    loading: {
      type: Boolean,
      default: false,
    },
    iconPosition: {
      type: String,
      default: 'left',
      validator(value) {
        return value === 'left' || value === 'right'
      },
    },
    disabled: {
      type: Boolean,
      default: false,
    },
    size: {
      type: String,
      default: 'middle',
      validator(value) {
        return ['large', 'middle', 'small'].indexOf(value) >= 0
      },
    },
    type: {
      type: String,
      default: 'default',
      validator(value) {
        return (
          [
            'dashed',
            'text',
            'primary',
            'default',
            'info',
            'error',
            'warning',
            'success',
          ].indexOf(value) >= 0
        )
      },
    },
}

具体含义如下:

参数 说明 类型 可选值 默认值
size 尺寸 string small / middle / large middle
type 类型 string primary / success / warning / error / info / text / dashed /default default
disabled 是否禁用状态 boolean false
icon 图标名称 string
iconPosition 图标位置 string left / right left
loading 是否加载中状态 boolean false

下面我就对代码做下解释,

  1. button一个动态的class,这个class是由computed计算属性得来,
computed: {
    classes() {
      return {
        [`icon-${this.iconPosition}`]: true,
        ['disabled']: this.disabled,
        [`y-button-${this.size}`]: true,
        [`y-button-${this.type}`]: true,
      }
    },
  },

这个的意思就是,根据用户传的参数来生成对应的class,然后在css中写对应的样式就可以了。

  1. button里面的两个icon组件,后面会介绍,主要是用来显示图标,第一行主要是控制按钮不在loading状态下显示图标(如果用户传了的话),第二行主要是控制显示loading图标的。

  2. 第三部分的slot就是用来显示按钮上面的文字。

  3. 还有一个click事件的监听,这里只是向外触发了一个事件,具体需要什么操作,根据用于自己实现,

onClick() {
    console.log('kk')
    if (this.disabled) {
        console.log('kk')
        return
    }
    this.$emit('click')
},
  1. 后面的就是css样式的编写,具体的样式这里就不放出了,自己写的样式也不太好看,如果有兴趣的可以查看结尾的GitHub地址,代码都上传在那里。

到此,Button组件就已经造完了,是不是很简单哈!

4、Button组件-遇到的问题

说实话,写这个组件的时候还没有遇到困难的问题,难一点的可能就是各种类型下的按钮样式了吧,一些设计上还是借鉴了其他的组件库,因为自己设计的实在是太丑了。

5、结束

第一次写这种技术类的文章,不太清楚应该怎么写好,有什么问题的可以私信或者留言,然后在更新后面组件文章会进行调整。

项目地址Yue UI

声明:本文内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎进行举报,并提供相关证据,工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。