提交 51fefce5 编写于 作者: DCloud-WZF's avatar DCloud-WZF 💬

refactor(directive): v-model

上级 96fcff23
......@@ -253,13 +253,20 @@
"navigationBarTitleText": "v-bind 组合式 API"
}
},
{
"path": "pages/directive/v-model/v-model",
"path": "pages/directive/v-model/v-model-options",
"style": {
"navigationBarTitleText": "v-model"
}
},
{
"path": "pages/directive/v-model/v-model-composition",
"style": {
"navigationBarTitleText": "defineModel"
}
},
{
"path": "pages/directive/v-slot/v-slot",
"style": {
......
<template>
<view>
<view class="mb-10 flex justify-between flex-row">
<text>v-model in Foo:</text>
<text id="model-value-text">{{ modelValue }}</text>
</view>
<view class="mb-10 flex justify-between flex-row">
<text>v-model:msg in Foo:</text>
<text id="model-msg-text">{{ msg }}</text>
</view>
<view class="mb-10 flex justify-between flex-row">
<text>defineModel num:</text>
<text id="model-num-text">{{ num }}</text>
</view>
<button class="mb-10" id="update-value-btn" @click="updateValue">
update value
</button>
</view>
</template>
<script setup lang="uts">
// 在被修改时,触发 "update:modelValue" 事件
const modelValue = defineModel({ type: String })
// 在被修改时,触发 "update:msg" 事件
const msg = defineModel('msg', { type: String, default: 'default msg' })
const num = defineModel('num', { type: Number, default: 1 })
const updateValue = () => {
modelValue.value += '1'
msg.value += '2'
num.value++
}
</script>
<template>
<view>
<view>child-component-count:{{number}}</view>
<button type="default" @click="add">+1</button>
</view>
</template>
<script>
export default {
props: {
number: {
type: Number,
default: 0
}
},
emits: ['update:number'],
methods: {
add() {
this.$emit('update:number', this.number + 1)
}
}
}
</script>
\ No newline at end of file
const PAGE_PATH = '/pages/directive/v-model/v-model-composition'
describe('defineModel', () => {
let page = null
beforeAll(async () => {
page = await program.reLaunch(PAGE_PATH)
await page.waitFor('view')
})
it('basic', async () => {
const modelValueText = await page.$('#model-value-text')
expect(await modelValueText.text()).toBe('str')
const modelValueInput = await page.$('#model-value-input')
expect(await modelValueInput.value()).toBe('str')
const modelMsgText = await page.$('#model-msg-text')
expect(await modelMsgText.text()).toBe('msg')
const modelMsgInput = await page.$('#model-msg-input')
expect(await modelMsgInput.value()).toBe('msg')
const modelNumText = await page.$('#model-num-text')
expect(await modelNumText.text()).toBe('1')
const updateValueBtn = await page.$('#update-value-btn')
await updateValueBtn.tap()
expect(await modelValueText.text()).toBe('str1')
expect(await modelValueInput.value()).toBe('str1')
expect(await modelMsgText.text()).toBe('msg2')
expect(await modelMsgInput.value()).toBe('msg2')
const handleModelValueUpdateRes = await page.$('#handle-model-value-update-res')
expect(await handleModelValueUpdateRes.text()).toBe('str1')
const handleModelMsgUpdateRes = await page.$('#handle-model-msg-update-res')
expect(await handleModelMsgUpdateRes.text()).toBe('msg2')
})
})
<template>
<view class="page">
<Foo
v-model="str"
v-model:msg="msg"
@update:modelValue="handleModelValueUpdate"
@update:msg="handleModelMsgUpdate" />
<input class="mb-10 input" id="model-value-input" v-model="str" />
<input class="mb-10 input" id="model-msg-input" v-model="msg" />
<view class="mb-10 flex justify-between flex-row">
<text>handle modelValue update res:</text>
<text id="handle-model-value-update-res">{{ handleModelValueUpdateRes }}</text>
</view>
<view class="mb-10 flex justify-between flex-row">
<text>handle model msg update res:</text>
<text id="handle-model-msg-update-res">{{ handleModelMsgUpdateRes }}</text>
</view>
</view>
</template>
<script setup lang="uts">
import Foo from './Foo-composition.uvue'
const str = ref('str')
const msg = ref('msg')
const handleModelValueUpdateRes = ref('')
const handleModelValueUpdate = (val : string) => {
handleModelValueUpdateRes.value = val
}
const handleModelMsgUpdateRes = ref('')
const handleModelMsgUpdate = (val : string) => {
handleModelMsgUpdateRes.value = val
}
</script>
<style>
.input {
padding: 8px 10px;
border: 1px solid #ccc;
border-radius: 4px;
}
</style>
const PAGE_PATH = '/pages/directive/v-model/v-model-options'
describe('v-model', () => {
let page
const platformInfo = process.env.uniTestPlatformInfo.toLowerCase()
const isIos = platformInfo.startsWith('ios')
beforeAll(async () => {
page = await program.reLaunch(PAGE_PATH)
await page.waitFor(500)
})
it('input', async () => {
const modelStrInput = await page.$('#model-str')
await modelStrInput.input('new str')
const str = await page.$('#str')
expect(await str.text()).toBe('new str')
if (!isIos) {
// TODO: ios 不支持 number & trim 修饰符
const modelNumInput = await page.$('#model-num')
await modelNumInput.input('123')
const typeofNum = await page.$('#typeof-num')
expect(await typeofNum.text()).toBe('number')
const modelStrTrimInput = await page.$('#model-str-trim')
await modelStrTrimInput.input(' trim ')
const strLength = await page.$('#str-length')
expect(await strLength.text()).toBe('4')
}
// TODO: lazy 修饰符仅 android 支持,补充测试
})
})
\ No newline at end of file
<template>
<view class="page">
<view class="mb-10 flex justify-between flex-row">
<text>str:</text>
<text id="str">{{ str }}</text>
</view>
<input class="mb-10 input" id="model-str" v-model="str" />
<input class="mb-10 input" id="model-num" v-model.number="num" type="text" />
<input class="mb-10 input" id="model-str-trim" v-model.trim="strForTrim" />
<input class="mb-10 input" id="model-str-lazy" v-model.lazy="str" type="text" />
<view class="mb-10 flex justify-between flex-row">
<text>typeof num:</text>
<text id="typeof-num">{{ typeof num }}</text>
</view>
<view class="mb-10 flex justify-between flex-row">
<text>str for trim length:</text>
<text id="str-length">{{ strForTrim.length }}</text>
</view>
</view>
</template>
<script lang="uts">
export default {
data(){
return {
str: 'str',
num: 1,
strForTrim: ' abc ',
}
},
}
</script>
<style>
.input {
padding: 8px 10px;
border: 1px solid #ccc;
border-radius: 4px;
}
</style>
const PAGE_PATH = '/pages/directive/v-model/v-model'
describe('v-model', () => {
let page
beforeAll(async () => {
page = await program.reLaunch(PAGE_PATH)
await page.waitFor(500)
})
it('input', async () => {
const value = Date.now() + ''
// TODO: 自动化测试web端存在问题
// 1. 直接获取 input 由于 web 端 input 为框架封装的自定义组件,所以被自动化测试框架识别为组定义组件,而不是 input element
// 2. 通过 class 获取标准 input element,自动化测试框架 isValidEl 限制只允许获取 uni element
if (process.env.uniTestPlatformInfo.startsWith('android')) {
const inputElement = await page.$('.input')
await inputElement.input(value)
const inputValueElement = await page.$('.input-value')
expect(await inputValueElement.text()).toBe(value)
}
})
})
\ No newline at end of file
<template>
<view class="page">
<view class="split-title">input</view>
<input class="input" v-model="inputValue" />
<text class="input-value">{{inputValue}}</text>
<view class="split-title">button</view>
<view>
<button type="default" @click="countPlus">+1</button>
<!-- TODO -->
<!-- <counter v-model:number="count"></counter> -->
</view>
</view>
</template>
<script>
// import counter from "./counter.uvue"
export default {
// components: {
// counter
// },
data() {
return {
inputValue: '',
count: 0
}
},
methods: {
countPlus() {
this.count++;
}
}
}
</script>
<style>
.input {
padding: 8px 10px;
border: 1px solid #ccc;
border-radius: 5px;
}
</style>
......@@ -806,6 +806,22 @@ export default {
},
]
},
{
id: 'v-model',
name: 'v-model',
children: [
{
id: 'v-model-options',
name: 'v-model',
url: 'v-model-options',
},
{
id: 'v-model-composition',
name: 'defineModel',
url: 'v-model-composition',
},
]
},
]
},
{
......
......@@ -159,7 +159,7 @@ function transform(fileInfo, api) {
- [x] v-for
- [x] v-on
- [x] v-bind
- [ ] v-model
- [x] v-model
- [ ] v-slot
- [x] v-pre
- [x] v-once
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册