Skip to content

Instantly share code, notes, and snippets.

@dogboydog
Created July 17, 2022 19:27
Show Gist options
  • Save dogboydog/e1aaba66fc61126242a8b3367dc51e6a to your computer and use it in GitHub Desktop.
Save dogboydog/e1aaba66fc61126242a8b3367dc51e6a to your computer and use it in GitHub Desktop.
given a directory with YarnSpinner-Unity csv files, convert to godot localization .csv format (python 3)
import csv
import pathlib
import os
import re
def fix_locale_code(code):
# https://docs.godotengine.org/en/stable/tutorials/i18n/locales.html
return code.replace("-", "_")
'''
Read all non-metadata csv files from unity YarnSpinner and convert them to a godot
localization file
'''
def main():
# adjust paths as necessary for your project
project_root = pathlib.Path(os.path.abspath(os.path.dirname(__file__)))
project_root = project_root.joinpath("..", "..", "..").resolve()
locales_dir = pathlib.Path(project_root).joinpath('core/ui/dialogue/localization/locales/')
converted_dir = locales_dir # use a different dir if you want while testing: pathlib.Path(project_root).joinpath("temp")
converted_dir.mkdir(parents=True, exist_ok=True)
locale_to_line_list_dict = dict()
locale_to_header_list_dict = dict()
for csvfile in locales_dir.glob('*.csv'):
if 'metadata.csv' in str(csvfile) or 'godot' in str(csvfile):
print(f"Ignoring file {csvfile}")
continue
with open(csvfile, 'r', encoding='utf-8-sig') as locale_csv:
print(f"Reading YS unity .csv {csvfile}")
locale_code = None
locale_csv_reader = csv.reader(locale_csv)
row_num = 0
current_headers = None
for row in locale_csv_reader:
if row_num == 0:
current_headers = row
print(f"Found csv headers {row}")
row_num += 1
continue
if row_num == 1:
locale_code = fix_locale_code(row[0])
print(f"Using locale name '{locale_code}'")
locale_to_line_list_dict[locale_code] = dict()
locale_to_header_list_dict[locale_code] = row
column = 0
line = dict()
line_id = None
for header_value in row:
header = current_headers[column].strip()
if header == 'id':
line_id = header_value.replace('line:', '')
# replace myKey with MY_KEY
line_id = re.sub("([a-z])([A-Z])", r"\g<1>_\g<2>", line_id).upper()
header = 'keys'
line[header] = header_value
column += 1
locale_to_line_list_dict[locale_code][line_id] = line
print(f"row #{row_num}: {line}")
row_num += 1
converted_headers = ['keys']
converted_headers.extend(locale_to_line_list_dict.keys())
converted_rows = []
line_id_to_line = dict()
locales = locale_to_line_list_dict.keys()
for locale in locale_to_line_list_dict.keys():
print(f"Restructuring line dict for locale {locale}")
for line_id in locale_to_line_list_dict[locale]:
line = locale_to_line_list_dict[locale][line_id]
if line_id not in line_id_to_line.keys():
line_id_to_line[line_id] = dict()
line_id_to_line[line_id][locale] = line['text']
# fill in any missing lines for a locale with empty string
for line_id in line_id_to_line.keys():
line = line_id_to_line[line_id]
line['keys'] = line_id
found_non_blank = False
for locale in locales:
if locale not in line:
line[locale] = ''
if len(line[locale]) > 0:
found_non_blank = True
if found_non_blank:
converted_rows.append(line)
with open(locales_dir.joinpath('godot_locales.csv'), 'w', encoding='utf-8') as converted_csv:
# make sure 'keys' is the first column
fieldnames = ['keys']
locales = [*converted_rows[0].keys()]
locales.remove('keys')
fieldnames.extend(locales)
writer = csv.DictWriter(converted_csv, fieldnames=fieldnames, lineterminator='\n')
writer.writeheader()
writer.writerows(converted_rows)
if __name__ == "__main__":
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment