DEV Community

Cover image for 5 ways of displaying i18n translations in Vue
Anzelika
Anzelika

Posted on

5 ways of displaying i18n translations in Vue

When your Vue app needs internalization, you'll probably come across i18n. It took me a while to get a proper grasp on how to display messages in different scenarios (especially #5), so I'm laying out a quick easy-digest summary here.

1. Basic interpolation

With the interpolation curly brackets you can render any content that can be placed directly in your template HTML.

<p>{{$t('introText')}}</p>

2. Binding the value

Useful for input placeholders or labels.

<v-text-field :label="$t('form.firstName')"></v-text-field>

3. Within a function

Note that within the Vue instance it would be necessary to use this keyword

btnLabel(){
  return this.$t('buttons.save')
}

4. Using v-t directive

With v-t directive you may specify the path of the translation string in the data object and then easily render it in the template.

data: () => ({
   path: "buttons.add"  
}),
 <v-btn v-t="path"></v-btn>

NB: This directive is not reactive, therefore the content needs to be manually reloaded when the locale changes.

5. Using v-text directive

To solve the reactivity problem, you may use v-text directive instead.

data: () => ({
   path: "buttons.add"  
}),
 <v-btn v-text="$t(path)"></v-btn>

Hope this comes in handy for our translation wizards! Give me a shout if there's a technique I missed 😜

Discussion (5)

Collapse
haruanm profile image
Haruan Justino

There is the v-t directive to prevent re-execution of the translation too.

Collapse
anzelika profile image
Anzelika Author • Edited

Oh, very cool! Honestly was not even aware of that. Will replace the 4th point with that, since it's much cleaner than v-text :)

Collapse
anzelika profile image
Anzelika Author

Though I just realised it's not reactive (if you change locale, it won't refresh the messages. v-text does though, without having to refresh the page. Do you know if there is a way to achieve reactivity with v-t?

Thread Thread
haruanm profile image
Haruan Justino • Edited

You will need to re-render the component.
This dirty workarround can be done in some ways listed here:
michaelnthiessen.com/force-re-render/

When I needed to, I used this:

<template>
  <my-component v-if="renderComponent" />
  export default {
    data() {
      return {
        renderComponent: true,
      };
    },
    methods: {
      forceRerender() {
        // Remove my-component from the DOM
        this.renderComponent = false;

        this.$nextTick(() => {
          // Add the component back in
          this.renderComponent = true;
        });
      }
    }
  };

and executed the forceRerender on watch for language change.

Collapse
m7salam profile image
Mo Salam

How to use it in v-model directly

For example if you have a price coming from the backend which is mapped to v-model directly

How can U use localisation on it directly?

Thanks