組件間傳值及傳值校驗
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>study</title>
<script src="https://unpkg.com/vue@next"></script>
</head>
<body>
<div id="root"></div>
</body>
<script>
const app = Vue.createApp({
data() {
return { num: 1111 }
},
template: `
<div><test :content="num" /></div>
`
});
// type:String, Boolean, Array, Object, Function, Symbol
// validator 校驗
// required 必填
// default 默認值
app.component('test', {
props: {
content: {
type: Number,
validator: function(value) {
return value < 500;
},
default: function() {
return 456;
}
}
},
template: `<div>{{content}}</div>`
});
const vm = app.mount('#root');
</script>
</html>
父組件獲取子組件的數據和執行子組件方法
- 調用子組件的時候定義一個 ref
<v-header ref="header" />
- 父組件獲取子組件數據
this.$refs.header.屬性
- 父組件執行子組件的方法
this.$refs.header.方法
子組件獲取父組件的數據和執行父組件方法
- 子組件獲取父組件的數據
this.$parent.數據
- 子組件獲取父組件的方法
this.$parent.方法
Vue3.x 父組件自定義事件,子組件給父組件傳值
- 子組件獲取父組件的方法
父組件中聲明自定義方法
<template>
<div>
<v-header @send="getChild"></v-header>
</div>
</template>
<script>
import Header from "./Header"
export default {
data() {
return {
title: "首頁組件"
}
},
methods: {
getChild(data) {
console.log(data + "home")
}
},
components: {
"v-header": Header
}
}
</script>
<style lang="scss">
</style>
子組件通過this.$emit調用該自定義的方法
<template>
<div>
<h2>頭部組件
--- <button @click="sendParent">執行父組件的自定義事件</button>
</h2>
</div>
</template>
<script>
export default {
// 建議定義所有發出的事件,以便更好地記錄組件應該如何工作
emits: ["send"],
data() {
return {
msg: "頭部組件"
}
},
methods: {
sendParent() {
// this.$emit("send")
this.$emit("send", this.msg)
}
}
}
</script>
<style lang="scss">
h2 {
text-align: center;
background: #000;
height: 44px;
line-height: 44px;
color: white;
}
</style>
比較高級的使用方式:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>study</title>
<script src="https://unpkg.com/vue@next"></script>
</head>
<body>
<div id="root"></div>
</body>
<script>
const app = Vue.createApp({
data() {
return { count: 1 }
},
template: `
<counter v-model="count" />
`
});
app.component('counter', {
props: ['modelValue'],
methods: {
handleClick() {
this.$emit('update:modelValue', this.modelValue + 1);
}
},
template: `
<div @click="handleClick">{{modelValue}}</div>
`
});
const vm = app.mount('#root');
</script>
</html>
雙向綁定高級部分
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>lesson 19</title>
<script src="https://unpkg.com/vue@next"></script>
</head>
<body>
<div id="root"></div>
</body>
<script>
const app = Vue.createApp({
data() {
return {
count: 'a',
}
},
template: `
<counter v-model.uppercase="count" />
`
});
app.component('counter', {
props: {
'modelValue': String,
'modelModifiers': {
default: ()=> ({})
}
},
methods: {
handleClick() {
let newValue = this.modelValue + 'b';
if(this.modelModifiers.uppercase) {
newValue = newValue.toUpperCase();
}
this.$emit('update:modelValue', newValue);
},
},
template: `
<div @click="handleClick">{{modelValue}}</div>
`
});
const vm = app.mount('#root');
</script>
</html>
非父子組件傳值
- 非父子組件傳值,借用 mitt 三方件
- 先安裝 mitt 插件:
npm install mitt --save - 實例化 mitt
mitt 的使用:<https://www.npmjs.com/package/mitt
import mitt from 'mitt';
const event = mitt();
export default event;
- 組件 A
<template>
<div>
<h2>頭部組件
----- <button @click="sendLogin">觸發登錄組件里面的事件 實現傳值</button>
</h2>
</div>
</template>
<script>
import event from "../model/event"
export default {
data() {
return {
msg: "頭部組件"
}
},
methods: {
sendLogin() {
//廣播事件
event.emit("toLogin", {
username: "張三",
age: 20
})
}
}
}
</script>
<style lang="scss">
h2 {
text-align: center;
background: #000;
height: 44px;
line-height: 44px;
color: white;
}
</style>
- 組件 B
<template>
<div class="login">
<input type="text" v-model="username" placeholder="用戶名" />
<br>
<input type="text" v-model="password" placeholder="密碼" />
<br>
<button @click="doLogin">執行登錄</button>
</div>
</template>
<script>
import event from "../model/event"
export default {
emits: {
submit: ({ username, password }) => {
if (username !== "" && password !== "") {
return true
} else {
console.log("用戶名密碼不能為空")
return false
}
}
},
data() {
return {
username: "",
password: ""
}
},
methods: {
doLogin() {
this.$emit("submit", {
username: this.username,
password: this.password
})
}
},
mounted() {
//監聽廣播
event.on("toLogin", (data) => {
console.log(data)
})
}
}
</script>
<style lang="scss">
.login {
padding: 20px;
}
</style>
持續更新中......