【Vue3学习笔记】setup

70 阅读1分钟

setup

基础使用:在setup中通过ref和reactive创建响应式数据

    <script>
    import { ref, reactive } from 'vue'

    export default {
      setup() {
        const msg = ref('hello world')
        const obj = reactive({
          name: '高启强',
          age: 43
        })
        return {
          msg,
          obj
        }
      }
    }
    </script>

    <template>
      <div>
        {{ msg }}
        <p>我是{{ obj.name }}</p>
      </div>
    </template>

Props和context

props就是父组件传入的属性;context是上下文对象,里面有attrs,slots,emit,expose

父组件

<template>
  <Child :name='obj.name' />
</template>

子组件

export default {
  props: ['name'],
  setup(props, context) {
    console.log('我是' + props.name);
    console.log(context.attrs)
    console.log(context.emit)
    console.log(context.slots)
    console.log(context.expose)
  }
}

context中的expose是做什么的?

expose官方称为:暴露公共属性,就是用来暴露给父组件的属性用的,暴露出去的属性在父组件可以访问到,没有暴露的属性获取不到,会是undefined。

子组件:在子组件中有name和age两个数据,只暴露出name数据

<script>
export default {
  props: ['name'],
  setup(props, { attrs, emit, slots, expose }) {
    const name = '张三'
    const age = 18
    // 只暴露出name,外面的组件只能获取到name,age就获取不到
    expose({
      name: name
    })

    return {
      name,
      age
    }
  }
}
</script>

父组件:父组件获取到name,获取不到age

    <script>
    import Child from '@/components/Child.vue'

    export default {
      components: { Child },
      mounted() {
        // 可以获取到name,获取不到age
        console.log(this.$refs.child.name);  // 张三
        console.log(this.$refs.child.age);   // undefined
      },
    }
    </script>

    <template>
      <div>
        <Child ref='child' />
      </div>
    </template>

data和setup中有相同的数据时会用哪个?

当data中有一个name,setup中也有一个name时,会用哪个呢?答案是setup, 当有相同名称的数据时候setup中的会代替data中的,也就是setup比data优先级高

    <script>
    import { ref } from 'vue'
    export default {
      data() {
        return {
          name: '高启兰',
        }
      },
      setup() {
        const name = ref('高启强')

        return {
          name
        }
      },
      created() {
        console.log(this.name);
      }
    }
    </script>

使用渲染函数h

在setup中一般是返回一个json对象,里面是data数据。但是setup也可以返回一个渲染函数。

因为返回的是渲染函数,渲染函数只是渲染当前是组件内容,没有返回其他数据。所以返回函数的话数据就只能在组件内部使用,不能在组件外部访问,因为没有return数据。

那怎么办呢?对了,可以使用expose将数据暴露出去就可以了

    <script>
    import { h, ref } from 'vue'

    export default {
      setup(props, { expose }) {
        const count = ref(0)

        // 此时父组件可以通过模板引用来访问这个 count 数据了。
        expose({
          count
        })

        return () => h('div', count.value)
      }
    }
    </script>

script setup

script setup是compsition api的一种写法,在script标签上加上setup,然后script就相当于是setup了,不需要自己导出数据直接使用,更加方便。

    <script setup>
    import { ref } from 'vue'
    import MyComponent from './MyComponent.vue'

    const count = ref(0)
    </script>

    <template>
    		<MyComponent />
    		<button @click="count++">{{ count }}</button>
    </template>