一. 传统写法不使用setup语法糖

方式一:通过v-model的方式实现子组件的显示与隐藏

  1. 父组件的内容
<template>
  <div>
    <el-button @click="open">打开</el-button>
    <Child v-model:visible="flag" ></Child>
  </div>
</template>
<script>
  import { ref, watch } from 'vue'
  import Child from "../components/Child.vue"
  export default {
    components: {
      Child
    },
    setup() {
      const flag = ref(false)
      const open = () => {
        flag.value = true
      }
      watch(() => flag.value , (val) => {
        console.log("监听flag值得变化:", val)
      })
      return {
        flag,
        open
      }
    }
  }
</script>
  1. 子组件内容
<template>
  <div class="hello">
    <el-dialog title="提示" v-model="dialogVisble" width="30%" :before-close="close">
      <span>这是一段信息</span>
      <template #footer>
        <span class="dialog-footer">
          <el-button @click="close">取 消</el-button>
          <el-button type="primary" @click="confirm">确 定</el-button>
        </span>
      </template>
    </el-dialog>
  </div>
</template>
<script>
  import { ref, watch } from 'vue'
  export default {
    props: {
      visible: {
        type: Boolean,
        default: false
      }
    },
    setup(props, ctx) {
      const dialogVisble = ref(false)
      const close = () => {
        ctx.emit("update:visible", false);
      };
      const confirm = () => {
        console.log('你点击了确定按钮')
        ctx.emit("update:visible", false);
      }
      watch(() => props.visible, (val) => {
        console.log(props.visible, val);
        dialogVisble.value = val
      });
      return {
        dialogVisble,
        confirm,
        close
      }
    }
  }
</script>

方式二:通过为元素绑定ref的方式实现子组件的显示与隐藏

  1. 父组件的内容
<template>
  <div>
    <el-button @click="open">打开</el-button>
    <Child ref="visibleDialog"></Child>
  </div>
</template>
<script>
  import { ref } from 'vue'
  import Child from "../components/Child.vue"
  export default {
    components: {
      Child
    },
    setup() {
      const visibleDialog = ref(null)
      const open = () => {
        visibleDialog.value.dialogVisble = true
      }
      return {
        visibleDialog,
        open
      }
    }
  }
</script>
  1. 子组件内容
<template>
  <div class="hello">
    <el-dialog title="提示" v-model="dialogVisble" width="30%" :before-close="close">
      <span>这是一段信息</span>
      <template #footer>
        <span class="dialog-footer">
          <el-button @click="close">取 消</el-button>
          <el-button type="primary" @click="confirm">确 定</el-button>
        </span>
      </template>
    </el-dialog>
  </div>
</template>
<script>
  import { ref } from 'vue'
  export default {
    setup(props, ctx) {
      const dialogVisble = ref(false)
      const confirm = () => {
        console.log('你点击了确定按钮')
        dialogVisble.value = false
      }
      const close = () => {
        dialogVisble.value = false
      }
      return {
        dialogVisble,
        confirm,
        close
      }
    }
  }
</script>

2. setup语法糖写法

  1. 父组件
<template>
  <Child :user="user" ref="visiableDialog"></Child>
  <el-button type="primary" @click="openDialog">打开弹窗</el-button>
</template>
<script setup>
import { reactive, ref } from 'vue'
import Child from "../components/childComponents.vue"
const visiableDialog = ref(null)
const user = reactive({
  name: '张三',
  age: 20
})
function openDialog() {
  visiableDialog.value.dialogVisble = true
  console.log(visiableDialog.value.dialogVisble);
}
</script>
  1. 子组件
<template>
  <div class="hello">{{ `${props.user.name}在学习VUE3` }}</div>
  <el-dialog title="提示" v-model="dialogVisble" width="30%">
    <span>这是一段信息</span>
    <template #footer>
      <span class="dialog-footer">
        <el-button @click="close">取 消</el-button>
        <el-button type="primary" @click="confirm">确 定</el-button>
      </span>
    </template>
  </el-dialog>
</template>
<script setup>
import { ref } from 'vue';
import { ElMessageBox } from 'element-plus'
// 定义控制弹窗显隐的变量
const dialogVisble = ref(false)
// 接受父组件传过来的值
// const props = defineProps({
//   user: {
//     type: Object,
//     default: {}
//   }
// })
// 或者
const props = defineProps(['user'])
function confirm() {
  ElMessageBox.confirm('确定关闭吗?').then(() => {
    console.log('你点击了确定按钮')
    dialogVisble.value = false
  }).catch(() => { })
}
function close() {
  dialogVisble.value = false
}
// 将变量暴露出来
defineExpose({
  dialogVisble
})
</script>

总结:

  • 对于传统写法两种方式来看,都有各自的优缺点,方式一在写法上虽然麻烦了些,但是符合vue的设计原则,尽量少的操作Dom,以操作数据的方式达到了预期的目的。
  • 而方式二看起来趋向于我们在vue2中的写法,虽然在写法上简便,但是在原理上则是操作了Dom,总之,两种方式都可以达到我们想要的结果,至于使用那种方式看个人编写代码的习惯吧。
  • 对于使用setup语法糖写法来看,代码整体比较整洁,写起来也相对方便快捷
声明:本站所有文章,如无特殊说明或标注,均为本站原创发布。任何个人或组织,在未征得本站同意时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理。