1,父子组件传递:
父组件传递参数
<template>
<div>
<!-- 子组件 参数:num 、nums -->
<child :num="nums.num" :doubleNum="nums.doubleNum" @increase="handleIncrease"></child>
</div>
</template>
<script setup lang="ts">
import child from './child.vue';
import { ref,reactive } from 'vue';
// 对象默认
const nums = reactive({
num: 0,
doubleNum: 0
});
// 点击事件
const handleIncrease = () => {
// 每次+1
nums.num++
// 每次+2
nums.doubleNum += 2
};
</script>
子组件接收参数
defineEmits: defineEmits() 宏仅限于 setup 语法糖 使用,用来声明组件要触发的事件。
<template>
<div>
<span>点击次数:{{ props.num }}</span><br/>
<span>双倍次数:{{ props.doubleNum }}</span><br/>
<el-button @click="handelClick">点击</el-button>
</div>
</template>
<script setup lang="ts">
import { ref } from 'vue';
// 声明组件要触发的事件 子传父之前触发
const emits = defineEmits(['increase']);
// 声明接收参数
const props = defineProps({
num: String,
doubleNum: String
});
// 点击事件 触发子传父
const handelClick = () => {
console.log('触发子组件点击')
// 触发父组件事件
emits('increase')
};
</script>
上是子组件
父组件接收触发:
<template>
<div>
<!-- 子组件 触发事件:handleIncrease -->
<child @increase="handleIncrease"></child>
<br />
我是父组件,我接收到的参数:<span v-if="data.name">姓名:{{data.name}}</span> <span v-if="data.age">, 年龄:{{data.age}}</span>
</div>
</template>
<script setup lang="ts">
import child from './child.vue';
import { ref,reactive } from 'vue';
// 接收对象封装
const data = reactive({
name: '',
age: ''
});
// 点击事件
const handleIncrease = (val : any) => {
data.name = val.name
data.age = val.age
};
</script>
父组件小改变特性:
<template>
<div>
<!-- 子组件 参数:对象 -->
<child v-bind="nums" @increase="handleIncrease"></child>
</div>
</template>
这实际上等价于:
<template>
<div>
<!-- 子组件 参数:num 、nums -->
<child :num="nums.num" :doubleNum="nums.doubleNum" @increase="handleIncrease"></child>
</div>
</template>
defineExpose 方式(常用)
概述: 这是我在 clone 项目模板中看到的使用方式,也属于最常用的方式。
在vue3中使用echarts图表切换路由时,返回后图表不显示:
解决方案:
拆开这么写,需要移除echarts自己生成的一个字段,莫名的出现。无解,且不可连写会报removeAttribute非函数形式。
vue3中创建项目的步骤:
输入命令创建:npm create vue@latest
输入项目名称:
是否添加ts,是否需要配置路由,是否需要pinia,是否开启Eslint(语法检查)开启后就会不能自由编写代码
vue3新特性:defineOptions和defineModel
defineOptions:当要修改组件名的时候,就可以用到该新特性了,其用法是(这个宏可以用来直接在 <script setup>
中声明组件选项,而不必使用单独的 <script>
块: )
defineOptions({
name:' 组件名称',
inheritAttrs: false, // 组件标签上的属性是否透传
customOptions: {/* 其他配置 */}
})
defineModel:子父组件通信,当父组件调用子组件,向子组件传参时(传name),使用let props1 = defineModel(‘name’)即可获取到
父组件需要使用v-model:name=“xxx”进行传参。当子组件接口父组件传来的参数字段后,子组件可以对其进行修改查看,一旦修改,父组件也会一并触发去修改。
defineModel() 返回的值是一个 ref。它可以像其他 ref 一样被访问以及修改,不过它能起到在父组件和当前变量之间的双向绑定的作用:
它的 value 和父组件的 v-model 的值同步;
当它被子组件变更了,会触发父组件绑定的值一起更新。
2、底层机制
defineModel 是一个便利宏。 编译器将其展开为以下内容:一个名为 modelValue 的 prop,本地 ref 的值与其同步;
一个名为 update:modelValue 的事件,当本地 ref 的值发生变更时触发。
父组件:
<template>
<Child v-model="value"></Child>
</template>
<script setup lang="ts">
import { ref } from "vue";
const value = ref("");
</script>
原子组件:
<template>
<input
:value="modelValue"
@input="emit('update:modelValue', $event.target.value)"
/>//当在子组件输入内容后,会传给父组件 从而形成双向绑定
//event.target.value 表示触发事件的表单元素的当前值。在大多数情况下,这个属性用于处理用户输入值的变化
</template>
<script setup lang="ts">
const props = defineProps(["modelValue"]);
const emit = defineEmits(["update:modelValue"]);
</script>
新特性 子组件:
<template>
<input type="text" v-model="model" />
</template>
<script setup lang="ts">
// model变量名称可随意取
const model = defineModel();
</script>
带参数的v-model
父组件Parent.vue
<template>
<Child v-model:date="dateValue"></Child>
</template>
<script setup lang="ts">
import { ref } from "vue";
const dateValue = ref("");
</script>
子组件Child.vue
1、vue3.4前用法(新特性前)
<template>
<input
type="text"
:value="date"
@input="emit('update:date', $event.target.value)"
/>
</template>
<script setup lang="ts">
const props = defineProps(["date"]);
const emit = defineEmits(["update:date"]);
</script>
1、vue3.4后用法(新特性后)
<template>
<input type="text" v-model="date" />
</template>
<script setup lang="ts">
const name = defineModel("date");
</script>
与上同情,当使用v-model:date时,可以绑定多个v-model:xxx进行像子组件传递
子组件也需要进行多方的接收进行双向绑定:(申明:可以绑定获取的值,也可以绑定父传子的字段名)
<template>
<input type="text" v-model="dateValue" />
<input type="text" v-model="dateTime" />
</template>
<script setup lang="ts">
const dateValue = defineModel("date");
const dateTimeValue = defineModel("dateTime");
</script>
父传子,子接收
父传子:
<HelloWorld msg="You did it!" />
子接收:
<script setup lang="ts">
defineProps<{
msg: string
}>()
</script>
子在模版中使用:
<h1 class="green">{{ msg }}</h1>