Annotation of modules/damieng/graphical_editor/loncapa_daxe/web/lcd_strings.dart, revision 1.4
1.1 damieng 1: /*
2: This file is part of LONCAPA-Daxe.
3:
4: LONCAPA-Daxe is free software: you can redistribute it and/or modify
5: it under the terms of the GNU General Public License as published by
6: the Free Software Foundation, either version 3 of the License, or
7: (at your option) any later version.
8:
9: LONCAPA-Daxe is distributed in the hope that it will be useful,
10: but WITHOUT ANY WARRANTY; without even the implied warranty of
11: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12: GNU General Public License for more details.
13:
14: You should have received a copy of the GNU General Public License
15: along with Daxe. If not, see <http://www.gnu.org/licenses/>.
16: */
17:
1.4 ! raeburn 18: // $Id: lcd_strings.dart,v 1.3 2024/03/25 17:21:14 raeburn Exp $
1.3 raeburn 19:
1.1 damieng 20: /// Provides localized strings.
21: library LCDStrings;
22:
23: import 'dart:async';
24: import 'dart:collection';
25: import 'dart:html' as h;
26: import 'package:intl/intl_browser.dart'; // or intl-standalone (see findSystemLocale)
27:
28:
29: /**
30: * Provides localized strings read from properties files.
31: * The current language file is read at application loading time.
32: */
33: class LCDStrings {
34:
35: static String resourcePath = "LocalStrings";
36: static HashMap<String, String> map = null;
37: static String systemLocale;
38: static const defaultLocale = 'en';
39:
40: static Future<bool> load() {
41: Completer<bool> completer = new Completer<bool>();
1.4 ! raeburn 42: getLCLanguage().then((String ul) {
! 43: if (ul != null)
! 44: systemLocale = ul;
1.1 damieng 45: else
46: systemLocale = defaultLocale;
47: String language = systemLocale.split('_')[0];
48: String fullFilePath = "${resourcePath}_$language.properties";
1.2 damieng 49: _request(fullFilePath, completer);
1.1 damieng 50: });
51: return(completer.future);
52: }
1.4 ! raeburn 53:
! 54: /*
! 55: * Customization to use a user's language preference in LON-CAPA if available,
! 56: * otherwise default to en.
! 57: *
! 58: * Post a message from the iframe to the parent with userlclang as data passed
! 59: * Listen for message posted back from parent with userlclang:locale
! 60: * where locale is one of LON-CAPA's supported languages:
! 61: * en de ar fa fr he ja ko pt ru tr zh. systemLocale will be set to this in
! 62: * load(). If no message is received within 500 ms, then completer completes
! 63: * and returns null, and load() will set systemLocale to default (en).
! 64: *
! 65: * A similar function is needed in strings.dart in daxe/lib/src because the UI
! 66: * contains strings from LocalStrings_<lang>.properties in daxe/lib/src
! 67: * and also from LocalStrings_<lang>.properties in loncapa_daxe/web
! 68: */
! 69:
! 70: static Future<String> getLCLanguage() {
! 71: Completer<String> completer = new Completer<String>();
! 72: String ul = null;
! 73: Duration delay = new Duration(milliseconds:500);
! 74: Timer lctimer = new Timer(delay,() {
! 75: if (!completer.isCompleted)
! 76: completer.complete(ul);
! 77: });
! 78: if (!completer.isCompleted) {
! 79: String msgtarget = h.window.location.protocol+'//'+h.window.location.hostname;
! 80: h.window.parent.postMessage('userlclang',msgtarget);
! 81: h.window.onMessage.listen((event) {
! 82: if (event.origin == msgtarget) {
! 83: List<String> msgdata = event.data.split(':');
! 84: if (msgdata[0] == 'userlclang') {
! 85: final RegExp usablelang = new RegExp("^(en|de|ar|fa|fr|he|ja|ko|pt|ru|tr|zh)\$");
! 86: if (usablelang.hasMatch(msgdata[1]))
! 87: ul = msgdata[1];
! 88: lctimer.cancel();
! 89: if (!completer.isCompleted)
! 90: completer.complete(ul);
! 91: }
! 92: }
! 93: });
! 94: }
! 95: return(completer.future);
! 96: }
1.1 damieng 97:
98: static String get(String key) {
99: return(map[key]);
100: }
101:
1.2 damieng 102: static void _request(String fullFilePath, Completer<bool> completer) {
103: h.HttpRequest request = new h.HttpRequest();
104: request.open("GET", fullFilePath);
105: request.onLoad.listen((h.ProgressEvent event) {
106: if (request.status == 404) {
107: // no localization for this language, use default instead
108: String defaultLanguage = defaultLocale.split('_')[0];
109: String defaultFullFilePath = "${resourcePath}_$defaultLanguage.properties";
110: if (fullFilePath == defaultFullFilePath)
111: completer.completeError("Error when reading the strings in $resourcePath");
112: else
113: _request(defaultFullFilePath, completer);
114: } else if (request.status != 200) {
115: completer.completeError("Error when reading the strings in $resourcePath");
116: } else {
117: _parseResponse(request.responseText);
118: completer.complete(true);
119: }
120: });
121: request.onError.listen((h.ProgressEvent event) {
122: completer.completeError("Error when reading the strings in $resourcePath");
123: });
124: request.send();
125: }
126:
127: static void _parseResponse(String txt) {
128: map = new HashMap<String, String>();
129: List<String> lines = txt.split("\n");
130: for (String line in lines) {
131: if (line.startsWith('#'))
132: continue;
133: int ind = line.indexOf('=');
134: if (ind == -1)
135: continue;
136: String key = line.substring(0, ind).trim();
137: String value = line.substring(ind + 1).trim();
138: map[key] = value;
139: }
140: }
1.1 damieng 141: }
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>