Replace translation system

This commit is contained in:
magiczocker10
2025-08-30 08:30:43 +02:00
committed by GitHub
parent 35321b5761
commit 5498d023db
19 changed files with 260 additions and 102 deletions

View File

Before

Width:  |  Height:  |  Size: 390 B

After

Width:  |  Height:  |  Size: 390 B

View File

Before

Width:  |  Height:  |  Size: 464 KiB

After

Width:  |  Height:  |  Size: 464 KiB

View File

@@ -15,8 +15,7 @@
<script type="text/javascript" src="./nintendogs+cats.js"></script>
<script type="text/javascript" src="./personalities.js"></script>
<script type="text/javascript" src="./items.js"></script>
<script type="text/javascript" src="./locale/en.js"></script>
<script type="text/javascript" src="./locale/de.js"></script>
<script type="text/javascript" src="./locale.js"></script>
<script type="text/javascript"><!--
/* service worker */
var FORCE_HTTPS=true;

67
nintendogs+cats/locale.js Normal file
View File

@@ -0,0 +1,67 @@
const Locale = ( function ( ui ) {
const VALID_LOCALES = [ 'de', 'en' ];
let _currentLocale = null;
let _currentLocaleAlt = null;
const _cachedLocales = {};
const _setSelectLanguageStatus = function ( status ) {
if ( document.getElementById( 'select-language' ) ) {
document.getElementById( 'select-language' ).disabled = !status;
}
};
const _setLocale = function ( langCode ) {
_currentLocale = _cachedLocales[ langCode ];
if ( /_alt$/.test( langCode ) ) {
_currentLocaleAlt = _cachedLocales[ langCode.replace( '_alt', '' ) ];
} else {
_currentLocaleAlt = null;
}
document.querySelectorAll( '*[data-translate-title]' ).forEach( ( elem ) => {
elem.setAttribute( 'title', '' );
elem.setAttribute( 'data-tooltip', Locale._( elem.getAttribute( 'data-translate-title' ) ) );
} );
document.querySelectorAll( '*[data-translate]' ).forEach( ( elem ) => {
elem.textContent = Locale._( elem.getAttribute( 'data-translate' ) );
} );
};
return {
_: function ( str ) {
if ( _currentLocale && _currentLocale[ str ] ) {
return _currentLocale[ str ];
} else if ( _currentLocaleAlt && _currentLocaleAlt[ str ] ) {
return _currentLocaleAlt[ str ];
}
return str;
},
set: function ( langCode ) {
if ( langCode === 'qqx' || _cachedLocales[ langCode ] ) {
_setLocale( langCode );
} else if ( VALID_LOCALES.includes( langCode ) ) {
const langCodeAll = langCode.replace( '_alt', '' );
// ui.toast( `Loading ${ langCodeAll.toUpperCase() } translation...`, 'locale' );
_setSelectLanguageStatus( false );
const script = document.createElement( 'script' );
script.type = 'text/javascript';
script.onload = function () {
// ui.toast( false, 'locale' );
_setSelectLanguageStatus( true );
_setLocale( langCode );
};
script.onerror = function () {
// ui.toast( 'Unexpected error: can\'t download locale file', 'locale' );
_setSelectLanguageStatus( true );
};
script.src = `./locale/${ langCodeAll }.js`;
document.head.appendChild( script );
}
},
add: function ( langCode, strings ) {
_cachedLocales[ langCode ] = strings;
}
};
}( UI ) );

View File

@@ -1,5 +1,5 @@
// Translations found in EUR
SavegameEditor.Constants.locale.de = {
Locale.add( 'de', {
// Food & Drinks
Item_Foods_Water: 'Wasser',
Item_Foods_Milk: 'Spezialmilch',
@@ -302,25 +302,25 @@ SavegameEditor.Constants.locale.de = {
Item_Lead_Brown: 'Braune Leine',
Item_Lead_Black: 'Schwarze Leine',
// Water Bowls
// Item_Dish_W_Stainless_1: '',
// Item_Dish_W_Bowl_Green_2: '',
// Item_Dish_W_Bowl_Yellow_3: '',
// Item_Dish_W_Bowl_Red_4: '',
// Item_Dish_W_Classic_5: '',
// Item_Dish_W_Pattern_6: '',
// Item_Dish_W_Western_7: '',
// Item_Dish_W_Wood_8: '',
// Water Bowls (currently untranslated)
Item_Dish_W_Stainless_1: 'Stainless Steel Bowl',
Item_Dish_W_Bowl_Green_2: 'Green Bowl',
Item_Dish_W_Bowl_Yellow_3: 'Yellow Bowl',
Item_Dish_W_Bowl_Red_4: 'Red Bowl',
Item_Dish_W_Classic_5: 'Urushi Bowl',
Item_Dish_W_Pattern_6: 'White Polka-Dot Bowl',
Item_Dish_W_Western_7: 'High-Class Bowl',
Item_Dish_W_Wood_8: 'Wooden Bowl',
// Food Bowls
// Item_Dish_White_1: '',
// Item_Dish_Bowl_Green_2: '',
// Item_Dish_Bowl_Yellow_3: '',
// Item_Dish_Bowl_Red_4: '',
// Item_Dish_Classic_5: '',
// Item_Dish_Pattern_6: '',
// Item_Dish_Western_7: '',
// Item_Dish_Wood_8: '',
// Food Bowls (currently untranslated)
Item_Dish_White_1: 'White Bowl',
Item_Dish_Bowl_Green_2: 'Green Bowl',
Item_Dish_Bowl_Yellow_3: 'Yellow Bowl',
Item_Dish_Bowl_Red_4: 'Red Bowl',
Item_Dish_Classic_5: 'Pottery Bowl',
Item_Dish_Pattern_6: 'Pink Polka-Dot Bowl',
Item_Dish_Western_7: 'Japanese-Style Bowl',
Item_Dish_Wood_8: 'Wooden Bowl',
// Interiors
Room_Norse: 'Nordeuropäisch',
@@ -332,4 +332,4 @@ SavegameEditor.Constants.locale.de = {
Room_Fairy: 'Märchen',
Room_Mario: 'Mario',
Room_Future: 'Futuristisch'
};
} );

View File

@@ -1,5 +1,5 @@
// Translations found in EUR
SavegameEditor.Constants.locale.en = {
Locale.add( 'en', {
// Food & Drinks
Item_Foods_Water: 'Water',
Item_Foods_Milk: 'Milk',
@@ -332,4 +332,4 @@ SavegameEditor.Constants.locale.en = {
Room_Fairy: 'Fairy Tale',
Room_Mario: 'Mario House',
Room_Future: 'Futuristic'
};
} );

View File

@@ -60,7 +60,7 @@
}
.item-name[ data-icon ]::before {
background-image: url( ./icons.webp );
background-image: url( ./assets/icons.webp );
background-repeat: no-repeat;
background-size: 68px;
content: '';
@@ -91,7 +91,7 @@
}
.item-icon {
background-image: url( ./items.webp );
background-image: url( ./assets/items.webp );
background-size: 576px;
background-repeat: no-repeat;
display: inline-block;

View File

@@ -27,11 +27,15 @@ for ( let j = 0; j < 34; j++ ) {
}
level_borders[ 99999 ][ 1 ] = 1203982336;
const allTexts = []; // Element, qqx name
SavegameEditor = {
Name: 'Nintendogs + Cats',
Filename: 'sysdata.dat',
/* Settings */
Settings: {
lang: 'en'
},
/* Constants */
Constants: {
MONEY_OFFSET: 0xA0,
@@ -109,8 +113,7 @@ SavegameEditor = {
[ '0x20E', 'Fairy Tale' ],
[ '0x20F', 'Mario House' ],
[ '0x210', 'Futuristic' ]
],
locale: {}
]
},
_write_money: function () {
@@ -186,10 +189,6 @@ SavegameEditor = {
getValue( 'interiors' )
);
},
getI18n: function ( loc, name ) {
const all = SavegameEditor.Constants.locale[ loc ] || SavegameEditor.Constants.locale.en;
return loc === 'qqx' ? name : all[ name ];
},
setPos: function ( node, pos ) {
const size = 64, // Sprite height
scale = 0.5, // height scaled down to 32px
@@ -219,8 +218,7 @@ SavegameEditor = {
itemInput = inputNumber( `supplies_${ index }`, index === 0 ? min : 0, type[ 1 ], tempFile.readU8( Number( item[ 2 ] ) ) );
itemIcon.className = 'item-icon';
itemName.className = 'item-name';
// itemName.textContent = SavegameEditor.getI18n( item[ 1 ] );
allTexts.push( [ itemName, item[ 1 ] ] );
itemName.dataset.translate = item[ 1 ];
SavegameEditor.setPos( itemIcon, index );
if ( item[ 3 ] ) {
itemName.dataset.icon = item[ 3 ];
@@ -257,6 +255,22 @@ SavegameEditor = {
row.prepend( col( 4, select( 'interiors', options, SavegameEditor.updateInterior ) ) );
row.prepend( col( 8, span( 'Active interior' ) ) );
},
/* settings */
loadSettings: function () {
if ( typeof localStorage === 'object' && localStorage.getItem( 'nintendogs-cats-settings' ) ) {
const loadedSettings = JSON.parse( localStorage.getItem( 'nintendogs-cats-settings' ) );
if ( typeof loadedSettings.lang === 'string' ) {
this.Settings.lang = loadedSettings.lang.toLowerCase().trim();
}
}
},
saveSettings: function () {
if ( typeof localStorage === 'object' ) {
localStorage.setItem( 'nintendogs-cats-settings', JSON.stringify( this.Settings ) );
}
},
preload: function () {
setNumericRange( 'money', 0, 9999999 );
setNumericRange( 'streetpass-met', 0, 9999999 );
@@ -290,6 +304,7 @@ SavegameEditor = {
SavegameEditor.appendItems();
SavegameEditor.appendInteriors();
Locale.set( SavegameEditor.Settings.lang );
},
unload: function () {
@@ -314,12 +329,6 @@ SavegameEditor = {
}
}
// Update item names
const loc = document.getElementById( 'select-language' ).value;
allTexts.forEach( ( t ) => {
t[ 0 ].textContent = SavegameEditor.getI18n( loc, t[ 1 ] );
} );
// Update supply-values
const supply_values = document.querySelectorAll( '[id^=number-supplies_]' );
supply_values.forEach( ( t ) => {
@@ -523,3 +532,14 @@ SavegameEditor = {
}
}
};
window.addEventListener( 'DOMContentLoaded', () => {
SavegameEditor.loadSettings();
document.getElementById( 'select-language' ).value = SavegameEditor.Settings.lang;
document.getElementById( 'select-language' ).addEventListener( 'change', ( e ) => {
SavegameEditor.Settings.lang = e.target.value;
Locale.set( e.target.value );
SavegameEditor.saveSettings();
} );
} );

View File

@@ -10,14 +10,7 @@
<link type="text/css" rel="stylesheet" href="../savegame-editor.css" media="all"/>
<script type="text/javascript" src="../savegame-editor.js"></script>
<script type="text/javascript" src="./picross-3d-round-2.js"></script>
<script type="text/javascript" src="./locale/en.js"></script>
<script type="text/javascript" src="./locale/de.js"></script>
<script type="text/javascript" src="./locale/es.js"></script>
<script type="text/javascript" src="./locale/es_alt.js"></script>
<script type="text/javascript" src="./locale/fr.js"></script>
<script type="text/javascript" src="./locale/fr_alt.js"></script>
<script type="text/javascript" src="./locale/it.js"></script>
<script type="text/javascript" src="./locale/ja.js"></script>
<script type="text/javascript" src="./locale.js"></script>
<script type="text/javascript" src="./puzzles.js"></script>
<script type="text/javascript"><!--
/* service worker */
@@ -60,10 +53,10 @@
<select id="select-language">
<option value="en">English</option>
<option value="de">Deutsch</option>
<option value="es">Español (EUR)</option>
<option value="es2">Español (USA)</option>
<option value="fr">Français (EUR)</option>
<option value="fr2">Français (USA)</option>
<option value="es">Español</option>
<option value="es_alt">Español latino</option>
<option value="fr">Français</option>
<option value="fr_alt">Français (Canada)</option>
<option value="it">Italiano</option>
<option value="ja">日本語</option>
<option value="qqx">System messages</option>

View File

@@ -0,0 +1,67 @@
const Locale = ( function ( ui ) {
const VALID_LOCALES = [ 'de', 'en', 'es_alt', 'es', 'fr', 'fr_alt', 'it', 'ja' ];
let _currentLocale = null;
let _currentLocaleAlt = null;
const _cachedLocales = {};
const _setSelectLanguageStatus = function ( status ) {
if ( document.getElementById( 'select-language' ) ) {
document.getElementById( 'select-language' ).disabled = !status;
}
};
const _setLocale = function ( langCode ) {
_currentLocale = _cachedLocales[ langCode ];
if ( /_alt$/.test( langCode ) ) {
_currentLocaleAlt = _cachedLocales[ langCode.replace( '_alt', '' ) ];
} else {
_currentLocaleAlt = null;
}
document.querySelectorAll( '*[data-translate-title]' ).forEach( ( elem ) => {
elem.setAttribute( 'title', '' );
elem.setAttribute( 'data-tooltip', Locale._( elem.getAttribute( 'data-translate-title' ) ) );
} );
document.querySelectorAll( '*[data-translate]' ).forEach( ( elem ) => {
elem.textContent = Locale._( elem.getAttribute( 'data-translate' ) );
} );
};
return {
_: function ( str ) {
if ( _currentLocale && _currentLocale[ str ] ) {
return _currentLocale[ str ];
} else if ( _currentLocaleAlt && _currentLocaleAlt[ str ] ) {
return _currentLocaleAlt[ str ];
}
return str;
},
set: function ( langCode ) {
if ( langCode === 'qqx' || _cachedLocales[ langCode ] ) {
_setLocale( langCode );
} else if ( VALID_LOCALES.includes( langCode ) ) {
const langCodeAll = langCode.replace( '_alt', '' );
// ui.toast( `Loading ${ langCodeAll.toUpperCase() } translation...`, 'locale' );
_setSelectLanguageStatus( false );
const script = document.createElement( 'script' );
script.type = 'text/javascript';
script.onload = function () {
// ui.toast( false, 'locale' );
_setSelectLanguageStatus( true );
_setLocale( langCode );
};
script.onerror = function () {
// ui.toast( 'Unexpected error: can\'t download locale file', 'locale' );
_setSelectLanguageStatus( true );
};
script.src = `./locale/${ langCodeAll }.js`;
document.head.appendChild( script );
}
},
add: function ( langCode, strings ) {
_cachedLocales[ langCode ] = strings;
}
};
}( UI ) );

View File

@@ -1,5 +1,5 @@
// Translations found in EUR
SavegameEditor.Constants.locale.de = {
Locale.add( 'de', {
prefix_puzzle: 'Nr. ',
prefix_skill: 'Fähigkeit ',
prefix_tutorial: 'Anleitung ',
@@ -406,4 +406,4 @@ SavegameEditor.Constants.locale.de = {
tutorial_5: 'Zahlen im Quadrat',
tutorial_6: 'Würfel kennzeichnen',
tutorial_7: 'Komplexe Aufgaben lösen'
};
} );

View File

@@ -1,5 +1,5 @@
// Translations found in EUR and USA
SavegameEditor.Constants.locale.en = {
Locale.add( 'en', {
prefix_puzzle: 'No. ',
prefix_skill: 'Skill ',
prefix_tutorial: 'Tutorial ',
@@ -406,4 +406,4 @@ SavegameEditor.Constants.locale.en = {
tutorial_5: 'Intro to Square Numbers',
tutorial_6: 'Flagging Cubes',
tutorial_7: 'Solving Big Puzzles'
};
} );

View File

@@ -1,5 +1,5 @@
// Translations found in EUR
SavegameEditor.Constants.locale.es = {
Locale.add( 'es', {
prefix_puzzle: 'N.º ',
prefix_skill: 'Técnica ',
prefix_tutorial: 'Tutorial ',
@@ -406,4 +406,4 @@ SavegameEditor.Constants.locale.es = {
tutorial_5: 'Números con cuadrado',
tutorial_6: 'Destacar los cubos',
tutorial_7: 'Puzles grandes'
};
} );

View File

@@ -1,5 +1,5 @@
// Translations found in USA
SavegameEditor.Constants.locale.es2 = {
Locale.add( 'es_alt', {
prefix_puzzle: 'N.º ',
prefix_skill: 'Técnica ',
prefix_tutorial: 'Tutorial ',
@@ -14,7 +14,7 @@ SavegameEditor.Constants.locale.es2 = {
puzzle_006: 'El número 2',
puzzle_007: 'Papas fritas',
puzzle_008: 'Cámara de cine',
puzzle_009: 'Rana ',
puzzle_009: 'Rana',
puzzle_010: 'Poni de juguete',
puzzle_011: 'La letra A',
puzzle_012: 'Hacha',
@@ -406,4 +406,4 @@ SavegameEditor.Constants.locale.es2 = {
tutorial_5: 'Números cuadrados',
tutorial_6: 'Señalar cubos',
tutorial_7: 'Rompecabezas grandes'
};
} );

View File

@@ -1,5 +1,5 @@
// Translations found in EUR
SavegameEditor.Constants.locale.fr = {
Locale.add( 'fr', {
prefix_puzzle: 'N° ',
prefix_skill: 'Technique ',
prefix_tutorial: 'Tutoriel ',
@@ -406,4 +406,4 @@ SavegameEditor.Constants.locale.fr = {
tutorial_5: 'Intro aux chiffres encadrés',
tutorial_6: 'Repérage de cubes',
tutorial_7: 'Casse-tête en gros bloc'
};
} );

View File

@@ -1,5 +1,5 @@
// Translations found in USA
SavegameEditor.Constants.locale.fr2 = {
Locale.add( 'fr_alt', {
prefix_puzzle: 'N° ',
prefix_skill: 'Habileté ',
prefix_tutorial: 'Tutoriel ',
@@ -406,4 +406,4 @@ SavegameEditor.Constants.locale.fr2 = {
tutorial_5: 'Intro aux chiffres carrés',
tutorial_6: 'Identifier les cubes',
tutorial_7: 'Résolution de gros casse-tête'
};
} );

View File

@@ -1,5 +1,5 @@
// Translations found in EUR
SavegameEditor.Constants.locale.it = {
Locale.add( 'it', {
prefix_puzzle: 'N. ',
prefix_skill: 'Tecnica ',
prefix_tutorial: 'Tutorial ',
@@ -406,4 +406,4 @@ SavegameEditor.Constants.locale.it = {
tutorial_5: 'I numeri inquadrati',
tutorial_6: 'Evidenziare i cubi',
tutorial_7: 'Risolvere puzzle grandi'
};
} );

View File

@@ -1,5 +1,5 @@
// Translations found in JPN
SavegameEditor.Constants.locale.ja = {
Locale.add( 'ja', {
prefix_puzzle: 'No.',
prefix_skill: 'テクニック',
prefix_tutorial: 'チュートリアル',
@@ -406,4 +406,4 @@ SavegameEditor.Constants.locale.ja = {
tutorial_5: '四角数字って?',
tutorial_6: 'マークの使い方',
tutorial_7: '大きなパズルを解くには?'
};
} );

View File

@@ -3,13 +3,17 @@
by Marc Robledo 2016
*/
const hexPos = [];
const textEle = [];
const reg = /\d+/;
SavegameEditor = {
Name: 'Picross 3D: round 2',
Filename: 'SAVEDATA',
/* Settings */
Settings: {
lang: 'en'
},
/* Constants */
Constants: {
BACKGROUND_OFFSET: 0x2232,
@@ -83,8 +87,7 @@ SavegameEditor = {
{ value: 9, name: 'Unlocked' },
{ value: 13, name: 'Solved' },
{ value: 29, name: 'Solved (Read)' }
],
locale: {}
]
},
_getProfileOffset: function () {
return this.Constants.PROFILES[ Number( getValue( 'profile-selector' ) ) - 1 ].offset;
@@ -257,17 +260,26 @@ SavegameEditor = {
SavegameEditor._update_list_values();
},
/* settings */
loadSettings: function () {
if ( typeof localStorage === 'object' && localStorage.getItem( 'picross-3d-round-2-settings' ) ) {
const loadedSettings = JSON.parse( localStorage.getItem( 'picross-3d-round-2-settings' ) );
if ( typeof loadedSettings.lang === 'string' ) {
this.Settings.lang = loadedSettings.lang.toLowerCase().trim();
}
}
},
saveSettings: function () {
if ( typeof localStorage === 'object' ) {
localStorage.setItem( 'picross-3d-round-2-settings', JSON.stringify( this.Settings ) );
}
},
/* check if savegame is valid */
checkValidSavegame: function () {
return ( tempFile.fileSize === 45688 );
},
getI18n: function ( loc, name ) {
const all = SavegameEditor.Constants.locale[ loc ] || SavegameEditor.Constants.locale.en,
tmp = all[ name ];
return loc === 'qqx' ? name : ( typeof tmp === 'string' ? tmp : tmp[ 0 ] );
},
preload: function () {
get( 'container-profile-name' ).appendChild( input( 'profile-name', 10 ) );
get( 'input-profile-name' ).addEventListener( 'change', function () {
@@ -300,11 +312,13 @@ SavegameEditor = {
rl = get( 'row-levels' ),
rs = get( 'row-skills' );
SavegameEditor.Constants.puzzles.forEach( ( puzzle, index ) => {
const idEle = span( '' );
const nameEle = span( '' );
const idEle = span( '' ),
idEle2 = span( '' ),
nameEle = span( '' );
nameEle.dataset.translate = puzzle;
if ( puzzle.startsWith( 'puzzle' ) ) {
const id = puzzle.replace( 'puzzle_', '' );
textEle.push( [ 'p', id, idEle, nameEle ] );
idEle.innerText = puzzle.replace( 'puzzle_', '' );
idEle2.dataset.translate = 'prefix_puzzle';
hexPos.push( [ 'puzzle', 0x220 + index * 16 ] );
rl.append(
col( 1, idEle ),
@@ -319,8 +333,8 @@ SavegameEditor = {
getField( `number-levels_${ index }_time` ).addEventListener( 'change', SavegameEditor._write_level_time );
getField( `number-levels_${ index }_points` ).addEventListener( 'change', SavegameEditor._write_level_points );
} else if ( puzzle.startsWith( 'tutorial' ) ) {
const id = puzzle.replace( 'tutorial_', '' ).replace( /^0/g, ' ' );
textEle.push( [ 't', id, idEle, nameEle ] );
idEle.textContent = puzzle.replace( 'tutorial_', '' ).replace( /^0/g, ' ' );
idEle2.dataset.translate = 'prefix_tutorial';
hexPos.push( [ 'tutorial', 0x220 + index * 16 ] );
rt.append(
col( 1, idEle ),
@@ -329,8 +343,8 @@ SavegameEditor = {
col( 3, select( `tutorials_${ index }_difficulty`, SavegameEditor.Constants.DIFFICULTIES, SavegameEditor._write_level_difficulty ) )
);
} else if ( puzzle.startsWith( 'skill' ) ) {
const id = puzzle.replace( 'skill_', '' ).replace( /^0/g, ' ' );
textEle.push( [ 's', id, idEle, nameEle ] );
idEle.textContent = puzzle.replace( 'skill_', '' ).replace( /^0/g, ' ' );
idEle2.dataset.translate = 'prefix_skill';
hexPos.push( [ 'skill', 0x220 + index * 16 ] );
rs.append(
col( 1, idEle ),
@@ -339,8 +353,10 @@ SavegameEditor = {
col( 3, select( `skills_${ index }_difficulty`, SavegameEditor.Constants.DIFFICULTIES, SavegameEditor._write_level_difficulty ) )
);
}
idEle.prepend( idEle2 );
} );
get( 'toolbar' ).children[ 0 ].appendChild( select( 'profile-selector', this.Constants.PROFILES, this._load_profile ) );
Locale.set( SavegameEditor.Settings.lang );
},
unload: function () {
@@ -353,21 +369,6 @@ SavegameEditor = {
tempFile.fileName = 'SAVEDATA';
tempFile.littleEndian = true;
const loc = document.getElementById( 'select-language' ).value,
i18n = {
p: SavegameEditor.getI18n( loc, 'prefix_puzzle' ),
s: SavegameEditor.getI18n( loc, 'prefix_skill' ),
t: SavegameEditor.getI18n( loc, 'prefix_tutorial' ),
easy: SavegameEditor.getI18n( loc, 'style_001' ),
medium: SavegameEditor.getI18n( loc, 'style_002' ),
hard: SavegameEditor.getI18n( loc, 'style_003' )
};
SavegameEditor.Constants.puzzles.forEach( ( puzzle, index ) => {
const tmp = textEle[ index ];
tmp[ 2 ].textContent = `${ i18n[ tmp[ 0 ] ] }${ tmp[ 1 ] }`;
tmp[ 3 ].textContent = SavegameEditor.getI18n( loc, puzzle );
} );
this._load_profile();
},
@@ -375,3 +376,14 @@ SavegameEditor = {
save: function () {
}
};
window.addEventListener( 'DOMContentLoaded', () => {
SavegameEditor.loadSettings();
document.getElementById( 'select-language' ).value = SavegameEditor.Settings.lang;
document.getElementById( 'select-language' ).addEventListener( 'change', ( e ) => {
SavegameEditor.Settings.lang = e.target.value;
Locale.set( e.target.value );
SavegameEditor.saveSettings();
} );
} );