【问题标题】:Show / hide html based on prop type on input根据输入的道具类型显示/隐藏html
【发布时间】:2020-10-08 01:39:54
【问题描述】:

我想根据道具类型在我的输入中显示和隐藏一个图标。

如果类型是密码,它将显示使密码可见/隐藏的图标;如果类型不是密码,它应该隐藏将 v-show 更改为 false 的图标。

这是带有 v-show showPwIcon 以使图标可见的 HTML

<input
  ref="textField"
  v-model="textField"
  :placeholder="placeholder"
  :type="type"
>
<span v-show="showPwIcon" @click="switchVisibility">
  <i :class="[pwIcon ? 'ri-eye-line' : 'ri-eye-off-line']"></i>
</span>

这里是 JS,没有 CSS,仅作为示例,v-show showPwIcon 默认设置为 false:

export default {
  props:{
    placeholder: {
      type: String,
      value: ''
    },
    type: {
      type: String,
      value: '',
      required: true
    }
  },
  data() {
    return {
      textField: '',
      showPwIcon: false,
      pwIcon: true
    }
  },
  watch: {
    type: function (password) {
      const inputType = this.$refs.textField.type
      if (inputType === 'password') {
      this.showPwIcon = true
    } else {
        this.showPwIcon = false
      }
    }
  },
  methods: {
    switchVisibility() {
      this.$emit('input', {
        type: this.$refs.textField.type = this.$refs.textField.type === 'password' ? 'text' : 'password'
      })
      if (this.$refs.textField.type === 'password') {
        this.pwIcon = true
      } else {
        this.pwIcon = false
      }
    }
  }
}

使用当前代码我遇到了这个问题:

输入文字不显示图标

<text-field-icon
  placeholder="Placeholder here"
  type="text"
/>

类型是密码但是v-show不是真的。

<text-field-icon
  placeholder="Placeholder here"
  type="password"
/>

我正在尝试通过查看输入上的道具类型来完成这项工作,但我无法通过this.$refs.textField.type 获取输入类型

示例代码https://codesandbox.io/s/vue-tailwind-template-dteq4

有什么想法吗?

【问题讨论】:

标签: javascript vue.js


【解决方案1】:

我们不需要 watcher$refs 来实现这一点。

注意$refs 不是反应式的

<input
  v-model="textField"
  :placeholder="placeholder"
  :type="inputType"
>
<span v-show="showPwIcon" @click="switchVisibility">
  <i :class="[pwIcon ? 'ri-eye-line' : 'ri-eye-off-line']"></i>
</span>
export default {
  props: {
    placeholder: {
      type: String,
      value: ""
    },
    type: {
      type: String,
      value: "",
      required: true
    }
  },
  data() {
    return {
      textField: "",
      pwIcon: false,
      inputType: this.type
    };
  },
  computed: {
    showPwIcon() {
      return this.type === "password";
    }
  },
  methods: {
    switchVisibility() {
      this.inputType = this.inputType === "password" ? "text" : "password";
      this.$emit("input", {
        type: this.inputType
      });
      this.pwIcon = this.inputType === "text";
      console.log(this.inputType, this.pwIcon);
    }
  }
};

【讨论】:

    【解决方案2】:

    您不需要复杂的观察者。如果您考虑UI = Function(State),那么您应该只依赖使用type prop 而不是从实际输入元素-this.$refs.textField.type 中读取类型的值。此外,请注意$refs非响应式

    简单的解决方案是

    <input
      v-model="textField"
      :placeholder="placeholder"
      :type="(showPwIcon && !pwIcon) ? 'text' : type">
    
    <span v-show="showPwIcon" @click="switchVisibility">
      <i :class="[pwIcon ? 'ri-eye-line' : 'ri-eye-off-line']"></i>
    </span>
    
    export default {
    
      // Props and data declaration...
    
      watch: {
        type: function (newVal) {
          if (newVal === 'password') {
            this.showPwIcon = true
    
            // Initially, set password visibility to false
            this.pwIcon = true
          } else {
            this.showPwIcon = false
          }
        }
      },
    
      methods: {
        switchVisibility() {
    
          // Toggle Visibility
          this.pwIcon = !this.pwIcon;
    
          this.$emit('input', {
            type: this.pwIcon ? 'text' : 'password'
          })
        }
      }
    }
    

    请记住,您的事实来源是您的组件实例,而不是 DOM。阅读$refs 就像您正在创建第二个事实来源。 $refs 专为非 Vue 兼容的库而设计,您需要与实际 DOM 对话。很少有例子是图表库、视频播放器等。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-12-07
      • 2020-04-12
      • 2012-06-15
      • 2017-04-01
      • 2013-07-22
      • 1970-01-01
      • 1970-01-01
      • 2012-08-11
      相关资源
      最近更新 更多