Dynamic Localisation (Runtime Data In Blueprints)

I’m working on a project where we need localised text to be updated by our client without recompiling the project. Changes need to automatically be pulled in from a file at runtime.

Unreal’s localisation system is great, but the .po files had to be compiled into binary locres. Which seems like it would require continuous deployment or Unreal’s Automation Tools.

So we’d gone down the route of reading a JSON (or CSV) file into a data table using ‘FillDataTableFromJsonFile’. However we just discovered that these nodes cause crashes in packaged builds and are not supported outside the editor. (Unreal Engine Issues and Bug Tracker (UE-64206))

This method uses IDs such as ‘6BW4’ to uniquely identify key value pairs, and then grabs the correct text from the column of the current language.

We’d really appreciate any support on solving this issue! Has anyone managed to find an effective work around?

You would need to deserialise the JSON file yourself at runtime, you can use FJsonSerializer::Deserialize for this and expose it to blueprints if needed.
Does the result need to be stored in a datatable? You could store it as a struct or nested set of structs, or manually populate the data table after I guess.

Thanks Dave,

So we can get the serialised data using the Low Entry plugins like this:

But we want to look up the data to use for localisation. Rows are IDs and columns are languages. This would mean languages can be changed from an external CMS and updated.

274512-table.jpg

So how do we take this raw JSON data and structure it so we can read from it easily?

Shout out to Low Entry for their plugins and support on this.
https://www.unrealengine.com/marketplace/en-US/profile/Low+Entry

They sent me the following:

You can read the data depending on how
the data in JSON is formatted.

If it’s stored in an object, so
basically {key=>value}, and the value
is a string, then you can just use the
“Get String” or “Get As String”
blueprint.

In your case, you could either have
{language=>{ID=>translation}} or
{ID=>{language=>translation}}.

In both cases you would first do “Get
Object” to get the {ID=>translation}
or {language=>translation} object,
then on that object, you would use
“Get String”.

Here’s a basic example of how that works for me. I’m storing the JSON object so that I’m not reading it from file every time.

“ID”: [
“Lang-0”,
“Lang-1”,
“Lang-2”,
“Lang-3”,
“Lang-4”
]

Hope that helps anyone else trying to achieve this!