---
title: Translations
description: Where the c15t banner and dialog text comes from in a Vue app, how
  c15t picks the visitor's language, and how to switch it at runtime.
group: frameworks
lastModified: "2026-10-10T16:01:45+01:00"
---
## Where the text comes from

The banner, dialog and IAB text comes from the translations in your Inth
project, or your self-hosted backend's configuration. The backend sends the
text for the visitor's language with the policy. Edit copy there, not in your
Vue code. The Vue plugin has no option for message overrides.

[Copy and translations](/docs/customization/translations) lists the message
keys and how to write labels that describe each action.

## How c15t picks the language

By default the browser's own language decides. With `manifest()`, c15t reads
`navigator.language` and resolves the text from the manifest. With
`hosted()`, the browser sends it as `Accept-Language` with the policy request
to `/init`. When your project has no text for that language, the policy's
fallback language applies.

`manifest()` bundles English base copy only. When a visitor resolves to
another language, the browser loads that language's base copy from your site
the first time it is needed. Each visitor downloads their own language only,
and English visitors download no extra copy.

The text direction follows the resolved language. Arabic, Hebrew and other
right-to-left languages render the banner and dialog with `dir="rtl"`, and a
default corner position mirrors.

## Follow your site's language

Bind the `language` prop of `ConsentRoot` to your site's current language.
When the prop changes, `ConsentRoot` stores the language and resolves the
policy again, which fetches the text in that language:

```vue
<ConsentRoot :language="locale" />
```

Without `ConsentRoot`, assign the language to `useConsentLanguage()`. A new
language runs init again, which fetches the banner and dialog text in that
language. Assigning the current language does nothing:

```vue title="src/LanguageSwitcher.vue"
<script setup lang="ts">
import { useConsentKernel, useConsentLanguage } from 'c15t/vue/vue-plugin';

const language = useConsentLanguage();
const kernel = useConsentKernel();

// Resolving again with `init()` loads the banner and dialog text in the
// new language.
const switchTo = (code: string) => {
	language.value = code;
	void kernel.commands.init();
};
</script>

<template>
	<button type="button" @click="switchTo('en')">English</button>
	<button type="button" @click="switchTo('de')">Deutsch</button>
</template>
```

The assignment alone loads the new text. The example's extra
`kernel.commands.init()` call repeats the request and is not needed.

## Text that does not come from translations

`ConsentDialogLink` and the `ConsentGate` placeholder read their default
text from the translations, in English until init has delivered copy. One
label in the Vue components is a c15t option instead. Set it in the visitor's
language when your site has more than one:

|Text|Where|How to change it|
|--|--|--|
|"Open privacy settings"|`ConsentDialogTrigger` label|Set the `triggerAriaLabel` option.|

## Verify

Set your browser's preferred language to one your project translates, open
the app in a private window and confirm the banner uses it. Switch the
language with your switcher and confirm the banner and dialog text change
without a page reload.
