Skip to content

Adding a Custom Localization

Overview of Localization

By default, the Vue PDF Viewer component includes built-in translations for five languages: English, Italian, Portuguese, Thai, and Chinese. If your preferred language isn’t available, you can follow this guide to easily add custom languages to suit your needs.

Tutorial for Adding Custom Localization

In this tutorial, we'll use Portuguese (pt_PT) as an example.

To start off, we first set the locale and localization props in the VPdfViewer component:

vue
<VPdfViewer locale="customLang" :localization="{ customLang: { .... } }" />

After setting the locale and localization props, we can override the available localization keys for the custom language.

INFO

Please note that you’ll need to specify each localization key. Any keys that are not overridden will be displayed as blank for tooltips or as undefined for labels. To avoid this, you can import Locales to ensure that any unspecified keys fall back to the imported language (e.g., ...Locales.en_US).

vue
<script setup lang="ts">
import { ref } from "vue";
import { VPdfViewer, Locales } from "@vue-pdf-viewer/viewer";

const customLang = ref("pt_PT");
    
const localization = {
  customLang: {
    // Import the English localization as a fallback
    ...Locales.en_US,
    firstPageLabel: "Ir para a primeira página",
    lastPageLabel: 'Última página',
  },
};
</script>

<template>
    <VPdfViewer
      :src="samplePDF" 
      locale="customLang"
      :localization="localization"
    />
</template>

Example of using the  object

Here is a complete example showing how to add Portuguese (pt_PT) localization without using the Locales object:

vue
<script setup lang="ts">
import { ref } from "vue";
import { VPdfViewer } from "@vue-pdf-viewer/viewer";

const customLang = ref("pt_PT");
</script>

<template>
    <VPdfViewer
      :scr="samplePDF" 
      locale="customLang"
      :localization="{
        customLang: {
          firstPageLabel: 'Ir para a primeira página',
          lastPageLabel: 'Última página',
          rotateClockwiseLabel: 'Girar no sentido horário',
          rotateCounterclockwiseLabel: 'Girar no sentido anti-horário',
          textSelectionLabel: 'Ativar ferramenta de seleção de texto',
          handToolLabel: 'Ativar ferramenta de mão',
          singlePageLabel: 'Página única',
          dualPageLabel: 'Página dupla',
          pageScrollingLabel: 'Rolagem página',
          verticalScrollingLabel: 'Rolagem vertical',
          wrappedScrollingLabel: 'Rolagem envolvida',
          documentPropertiesLabel: 'Propriedades do documento',
        },
      }"
    />
</template>
vue
<script setup>
import { ref } from "vue";
import { VPdfViewer } from "@vue-pdf-viewer/viewer";

const customLang = ref("pt_PT");
</script>

<template>
    <VPdfViewer
      :scr="samplePDF" 
      locale="customLang"
      :localization="{
        customLang: {
          firstPageLabel: 'Ir para a primeira página',
          lastPageLabel: 'Última página',
          rotateClockwiseLabel: 'Girar no sentido horário',
          rotateCounterclockwiseLabel: 'Girar no sentido anti-horário',
          textSelectionLabel: 'Ativar ferramenta de seleção de texto',
          handToolLabel: 'Ativar ferramenta de mão',
          singlePageLabel: 'Página única',
          dualPageLabel: 'Página dupla',
          pageScrollingLabel: 'Rolagem página',
          verticalScrollingLabel: 'Rolagem vertical',
          wrappedScrollingLabel: 'Rolagem envolvida',
          documentPropertiesLabel: 'Propriedades do documento',
        },
      }"
    />
</template>
vue
<script lang="ts">
import { defineComponent } from "vue";
import { VPdfViewer } from "@vue-pdf-viewer/viewer";
    
export default defineComponent({
  components: { VPdfViewer },
  data() {
    return {
      samplePDF: "/sample.pdf",
      customLang: "pt_PT",
    } 
  }
})
</script>

<template>
    <VPdfViewer
      :src="samplePDF"
      locale="customLang"
      :localization="{
        customLang: {
          firstPageLabel: 'Ir para a primeira página',
          lastPageLabel: 'Última página',
          rotateClockwiseLabel: 'Girar no sentido horário',
          rotateCounterclockwiseLabel: 'Girar no sentido anti-horário',
          textSelectionLabel: 'Ativar ferramenta de seleção de texto',
          handToolLabel: 'Ativar ferramenta de mão',
          singlePageLabel: 'Página única',
          dualPageLabel: 'Página dupla',
          pageScrollingLabel: 'Rolagem página',
          verticalScrollingLabel: 'Rolagem vertical',
          wrappedScrollingLabel: 'Rolagem envolvida',
          documentPropertiesLabel: 'Propriedades do documento',
        },
      }"
    />
</template>
vue
<script>
import { defineComponent } from "vue";
import { VPdfViewer } from "@vue-pdf-viewer/viewer";
    
export default defineComponent({
  components: { VPdfViewer },
  data() {
    return {
      samplePDF: "/sample.pdf",
      customLang: "pt_PT",
    } 
  }
})
</script>

<template>
    <VPdfViewer
      :src="samplePDF"
      locale="customLang"
      :localization="{
        customLang: {
          firstPageLabel: 'Ir para a primeira página',
          lastPageLabel: 'Última página',
          rotateClockwiseLabel: 'Girar no sentido horário',
          rotateCounterclockwiseLabel: 'Girar no sentido anti-horário',
          textSelectionLabel: 'Ativar ferramenta de seleção de texto',
          handToolLabel: 'Ativar ferramenta de mão',
          singlePageLabel: 'Página única',
          dualPageLabel: 'Página dupla',
          pageScrollingLabel: 'Rolagem página',
          verticalScrollingLabel: 'Rolagem vertical',
          wrappedScrollingLabel: 'Rolagem envolvida',
          documentPropertiesLabel: 'Propriedades do documento',
        },
      }"
    />
</template>

Here is a screenshot of the labels overriden in the codes: Example of the labels overriden in the codes

If a localization key is not overridden, it will appear blank, as shown in the tooltip in the image below: Example of the labels not overriden

Using Prop with v-bind

When using v-bind to apply additional props, be careful about its placement relative to specific prop definitions. If v-bind="defaultProps" is placed after explicitly defined props (e.g., locale or localization), any matching keys within defaultProps will override the explicitly set values.

For example:

vue
<script setup>
import { ref } from 'vue';

const customLang = ref("pt_PT");
    
const defaultProps = ref({
  localization: {
    overriddenLang: {
      handToolLabel: 'Overridden Hand Tool Label',
      firstPageLabel: 'Overridden First Page Label',
    },
  },
});
</script>

<!-- Example A: Explicit props are preserved, as v-bind comes first -->
<VPdfViewer
  v-bind="defaultProps"
  locale="customLang"
  :localization="{
    customLang: {
      handToolLabel: 'Ativar ferramenta de mão',
      firstPageLabel: 'Ir para a primeira página',
    },
  }"
/>

<!-- Example B: Explicit props may be overridden by defaultProps, as v-bind comes last -->
<VPdfViewer
  locale="customLang"
  :localization="{
    customLang: {
      handToolLabel: 'Ativar ferramenta de mão',
      firstPageLabel: 'Ir para a primeira página',
    },
  }"
  v-bind="defaultProps"
/>

In Example A, The localization object will be preserved. In Example B, if defaultProps contains locale or localization, it will override these values.