【发布时间】:2019-11-29 18:33:18
【问题描述】:
我制作了一个自定义数字输入框组件,并希望它在点击时激活。该组件由 3 个元素、两个按钮(用于减少和增加数值)和一个输入组成,其中显示数字并可以手动更改。问题是父div (.numberField) 的@click 仅在单击输入框时触发,而不是在单击按钮时触发。
由于输入框似乎可以正常工作,我尝试将按钮元素更改为 input[type=button] 元素,但失败了。
我检查了@click 的子元素(两个按钮和输入)何时触发,并确认它们都以相同的方式运行(它们不会在设置:disabled="false" 的初始单击时触发他们每个人)
如果重要的话,我的 Vue 版本是 3.7.0
<template>
<div class="numberField" @click="fieldClicked">
<button @click="stepDown()" :disabled="disabled" class="left">
−
</button>
<input
v-model="value"
type="number"
:max="max"
:min="min"
:step="step"
:disabled="disabled">
<button @click="stepUp()" :disabled="disabled" class="right">
+
</button>
</div>
</template>
<script>
export default {
name: 'NumberField',
props: {
defaultValue: Number,
max: Number,
min: Number,
step: Number,
disabled: Boolean,
},
data() {
return {
value: this.defaultValue,
};
},
watch: {
value() {
this.value = Math.min(this.max, Math.max(this.min, this.value));
},
},
methods: {
stepDown() {
this.value -= this.step;
},
stepUp() {
this.value += this.step;
},
fieldClicked(event) {
// @click.stop will stop all clicks from propagating; we will only stop clicks when the field is active
if (!this.disabled) event.stopPropagation()
},
},
};
</script>
<style scoped>
.numberField {
display: flex;
flex-direction: row;
justify-content: center;
align-items: center;
height: 3em;
width: 8em;
}
.left {
border-top-left-radius: 0.2em;
border-bottom-left-radius: 0.2em;
}
.right {
border-top-right-radius: 0.2em;
border-bottom-right-radius: 0.2em;
}
input, button {
padding: 0;
border-radius: 0;
min-width: 0;
height: 100%;
width: 33%;
min-height: 0;
font-size: 1rem;
text-align: center;
}
</style>
这是我如何使用这个组件的总结:
<div class="item" v-for="item in items" :key="item.id" @click="toggleItem(item.id)" :class="{ active: activeItems[item.id] }">
<h1>{{ item.name }}, some other elements irrelevant are here too</h1>
<NumberField
:defaultValue="item.amount"
:max="item.amount"
:min="1"
:step="1"
:disabled="!activeItems[item.id]"></NumberField>
</div>
toggleItem(id) 切换 activeItems[item.id] 的布尔值。 NumberField 在项目处于非活动状态时被禁用。
我的期望是单击.numberField 的任何子元素会触发.numberField 的@click,然后(仅当该项目处于非活动状态时)然后传播到@987654337 的@click @,但似乎只有在单击 input[type=number] 时才会出现这种情况。
我会很感激任何帮助,我完全迷路了!
【问题讨论】:
-
为了实现你应该使用 $emit/$on 事件,vuejs.org/v2/guide/components-custom-events.html
-
您在观察问题时能否确认
disabled设置为true? -
父元素是什么意思?那个带有
numberField类的div?顺便说一句,您的fieldClicked错过了event参数。 -
@Thamerbelfkih 我不确定这会有什么帮助。我将无法发出事件,因为 \@click 对这些按钮不起作用,因为它们已被禁用
-
@skirtle 是的,我最初使用的 NumberField 实例已禁用:true。单击输入字段时,它会更改为 false,单击任何一个按钮时都不会。它更改为 false,因为
.numberField的@click被传播到div(NumberField 实例的父级),它更改了作为disabled属性传递的值
标签: vue.js