๐ Internationalization
March 22, 2024 ยท View on GitHub
Internationalization (sometimes abbreviated "i18n") refers to supporting multiple languages in a software project. This often means maintaining translations of text strings used in the project and letting users choose which translation they receive (or detecting it from their browser settings).
p5.js uses internationalization in a bunch of areas (our contributor docs, the official website, the reference, etc). We're expanding to include the console output of p5.js (which is primarily developer-facing error messages) in our internationalization efforts.
Tooling
We've integrated i18next into the codebase. Currently we only use it in the un-minified build of p5.js. p5.min.js only includes the outer layer of our internationalization code and does not use it.
Setup
We set up our i18next integration in src/core/internationalization.js and the translations are in translations/.
We set up the translation engine and autodetect the user's language from their browser settings before the p5 sketch is initialized. This ensures we can use translations for any errors we encounter in sketch setup() and preload().
(If we encounter any errors in language autodetection, we fall back to English.)
No translations in p5.min.js
There is specific logic in the browserify build task and src/core/init.js to avoid loading or setting up translations in the minified build. Adding translations does not increase the size of the minified build.
Using translations
To use translations include this line at the top of the file.
import { translator } from './internationalization';
Simple messages
Without internationalization you might log a message with the text inline.
console.log('Loading your sketch right now!')
Instead, you use translator:
console.log(translator('sketch.loading'))
This tells the translator to get the "sketch.loading" message in whatever language we've detected that the user prefers.
Dynamic messages
You can also inject variables into a translated message. For example,
console.log('I couldnt find ' + file.name + '. Are you sure it's there?')
would become something like
console.log(translator('fileLoading.notFound', { fileName: file.name }))
Translations like this expect the variables it uses to have a certain name, so make sure you use that. Check a translation file (look in translations/{YOUR_LANGUAGE}/) to see what the variable name is. You'll find the translation under the object path in the translation key.
"fileLoading.notFound" would be found at
{
"fileLoading": {
"notFound": "I couldnt find {{fileName}}. Are you sure it's there?"
}
}
Variables are framed in "{{ }}".
Modifying translations
Simply open translations/{YOUR_LANGUAGE}/translation.json, find the translation with the key (like in the example just above) and edit away!
Adding translations for new languages
The easiest way to do this is to add your language code (like "de" for German, "it" for Italian, etc) to the locales list in package.json and then from the terminal run '$ npm run build'.
This will generate you a fresh translations file in translations/{LANGUAGE_CODE}/! Now you can begin populating it with your fresh translations! ๐ฅ
You'll also need to add an entry for it in translations/index.js and translations/dev.js. You can follow the pattern used in that file for en and es.
Testing changes
The bulk of translations are not included in the final library, but are hosted online and are automatically downloaded by p5.js when it needs them. Updates to these only happen whenever a new version of p5.js is released.
However, if you want to see your changes (or any other changes which aren't released yet), you can simply run npm run dev which will build p5.js configured to use the translation files present locally on your computer, instead of the ones on the internet.
Further Reading
See the i18next translation function documentation. Everything documented above is just a subset of their functionality.