Andreas Hunter
Andreas Hunter

Reputation: 5024

Set focus text field inside dialog when dialog opened

I have custom text field and I must focus it functionality when dialog is opened. I tried focus it using vue.js refs:

Code:

<v-app id="app">
  <v-row align="center">
    <v-col class="text-center" cols="12">
      <v-btn color="primary" @click="openDialog()">Open dialog</v-btn>
    </v-col>
  </v-row>
  <v-dialog v-model="dialog">
   <v-card>
    <v-card-title
      class="headline grey lighten-2"
      primary-title
    >
      Dialog
    </v-card-title>
    <v-card-text>
      <v-row>
        <v-col cols="6" class="ml-2">
            <v-text-field
              ref="name"
              placeholder="Enter your name..."
              type="text"
              solo
              flat
              outlined
            ></v-text-field>
            <v-btn 
              color="indigo" 
              dark 
              @click = "setFocusName()"
             >Set focus</v-btn>
        </v-col>
      </v-row>
    </v-card-text>
   </v-card>
  </v-dialog>
</v-app>

Javascript:

new Vue({
  el: '#app',
  vuetify: new Vuetify(),
  data () {
    return {
      dialog: false
    }
  },
  methods: {    
    setFocusName() {
      this.$refs.name.focus();
    },

    openDialog() {
      this.dialog = !this.dialog  
      this.setFocusName()
    }
  }
});

When I click to open dialog button my text field not focused. Here you can see my full codepen

How I can focus it correctly when dialog is opened?

Upvotes: 9

Views: 5397

Answers (3)

XMehdi01
XMehdi01

Reputation: 1

Just add the autofocus property and it will set the focus on v-text-field inside dialog when dialog opened:

<v-text-field
              autofocus
              placeholder="Enter your name..."
              type="text"
              solo
              flat
              outlined
            ></v-text-field>

Upvotes: 3

I set the focus logic inside a watcher of the property that toggles the dialog.

watch: {
   dialog: function(value) {
      if (value) {
        setTimeout(() => {
          this.$refs.inputrefname.$refs.input.focus();
       });
     }
   }
}

Upvotes: 1

Jesper
Jesper

Reputation: 3834

The problem with your code is that you're trying to access the $ref before it's actually rendered, here's a sandbox with the working code: https://codepen.io/Djip/pen/ZEYezzm?editors=1011

To resolve the bug i've added a setTimeout to trigger the focus after 0.2 seconds from the open of the dialog. I first tried with $nextTick, but that wasn't enough to do the job - you can try adjusting the timer, to make it as low as possible.

setFocusName() {
  this.$refs.name.focus();
},

openDialog() {
  this.dialog = !this.dialog  
  setTimeout(() => {
    this.setFocusName()
  }, 200)
}

Upvotes: 5

Related Questions