vuetify icon indicating copy to clipboard operation
vuetify copied to clipboard

feat(VNumberInput): strict precision

Open J-Sek opened this issue 6 months ago • 1 comments

Description

Leaving precision unrestricted enables users to accidentally input invalid values. While it does not seem critical, QA engineers like to point out small things and bother developers. Most of the frameworks support precision prop (with default 0) and it looks like a sensible choice for Vuetify as well.

Resolves #19898

Notes about implementation:

  • replaced vTextFieldRef with inputText
    • allows us to format (enforce precision) value on blur and on model change
  • replaced onChange with onBlur
    • keeps clearable working

Markup:

<template>
  <v-app theme="dark">
    <v-container>
      <v-card class="mx-auto pa-6 my-4" style="max-width: 1200px">
        <v-row>
          <v-col cols="4">
            <small class="d-block mb-2">(dynamic precision clearable)</small>
            <v-number-input v-model="value1" :precision="precision1" clearable></v-number-input>
            <code>value: {{ value1 ?? "(empty)" }}</code>
            <br>precision: <input class="ml-3 px-2 border" type="number" v-model="precision1"></input>
          </v-col>
          <v-col cols="4">
            <small class="d-block mb-2">(:precision="1" :step=".2")</small>
            <v-number-input v-model="value2" :precision="1" :step=".2"></v-number-input>
            <code>value: {{ value2 ?? "(empty)" }}</code>
          </v-col>
          <v-col cols="4">
            <small class="d-block mb-2">(:max="20" :min="-10" :precision="0")</small>
            <v-number-input v-model="value3" :max="20" :min="-10" :precision="0"></v-number-input>
            <div class="d-flex align-center justify-space-between">
              <code>value: {{ value3 ?? "(empty)" }}</code>
              <div class="text-right">
                <v-btn @click="value2 = 5.125">Set to 5.125</v-btn>
                <v-btn @click="value2 = NaN">Set to NaN</v-btn>
              </div>
            </div>
          </v-col>
        </v-row>
      </v-card>
    </v-container>
  </v-app>
</template>

<script setup lang="ts">
  import { ref } from 'vue'

  const value1 = ref<number | null>(0.21)
  const precision1 = ref<number>(2)

  const value2 = ref<number>(0.2 + 0.1)
  const value3 = ref<number>(-10.25)
</script>

J-Sek avatar Jul 30 '24 12:07 J-Sek