1 /*
2  * Seven Kingdoms: Ancient Adversaries
3  *
4  * Copyright 2018 Jesse Allen
5  *
6  * This program is free software: you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation, either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
18  *
19  */
20 
21 //Filename    : LocaleRes.cpp
22 //Description : Locale Resources
23 
24 #ifdef ENABLE_NLS
25 #include <libintl.h>
26 #include <locale.h>
27 #endif
28 
29 #include <ALL.h>
30 #include <ODB.h>
31 #include <ConfigAdv.h>
32 #include <LocaleRes.h>
33 
34 //------------- End of function Constructor -------//
35 //
LocaleRes()36 LocaleRes::LocaleRes()
37 {
38 	lang[0] = 0;
39 	fontset[0] = 0;
40 	codeset[0] = 0;
41 	init_flag = 0;
42 #ifdef ENABLE_NLS
43 	cd = (iconv_t)-1;
44 	cd_latin = (iconv_t)-1;
45 	cd_from_sdl = (iconv_t)-1;
46 #endif
47 	in_buf = NULL;
48 	out_buf = NULL;
49 }
50 //------------- End of function Constructor -------//
51 
52 
53 //----------- Begin of function Destructor -------//
54 //
~LocaleRes()55 LocaleRes::~LocaleRes()
56 {
57 	deinit();
58 }
59 //------------- End of function Destructor -------//
60 
61 
62 //-------- Begin of function LocaleRes::init -----------//
63 //
64 #define INIT_BUF_SIZE 2048
init()65 void LocaleRes::init()
66 {
67 #ifdef ENABLE_NLS
68 	const char *env_locale_dir;
69 	if( misc.is_file_exist("locale") )
70 		bindtextdomain(PACKAGE, "locale");
71 	else if( env_locale_dir = getenv("SKLOCALE") )
72 		bindtextdomain(PACKAGE, env_locale_dir);
73 	else
74 		bindtextdomain(PACKAGE, LOCALE_DIR);
75 	textdomain(PACKAGE);
76 
77 	load();
78 
79 	in_buf = mem_add(INIT_BUF_SIZE+1);
80 	in_buf_size = INIT_BUF_SIZE;
81 	out_buf = mem_add(INIT_BUF_SIZE+1);
82 	out_buf_size = INIT_BUF_SIZE;
83 #endif
84 
85 	init_flag = 1;
86 }
87 //---------- End of function LocaleRes::init ----------//
88 
89 
90 //----------- Start of function LocaleRes::deinit ---------//
91 //
deinit()92 void LocaleRes::deinit()
93 {
94 	if( !init_flag )
95 		return;
96 #ifdef ENABLE_NLS
97 	if( cd != (iconv_t)-1 )
98 		iconv_close(cd);
99 	if( cd_latin != (iconv_t)-1 )
100 		iconv_close(cd_latin);
101 	cd = (iconv_t)-1;
102 	cd_latin = (iconv_t)-1;
103 #endif
104 	if( in_buf )
105 		mem_del(in_buf);
106 	if( out_buf )
107 		mem_del(out_buf);
108 	init_flag = 0;
109 }
110 //------------- End of function LocaleRes::deinit ---------//
111 
112 
113 //----------- Start of function LocaleRes::change_locale ---------//
114 //
load()115 void LocaleRes::load()
116 {
117 #ifdef ENABLE_NLS
118 	setlocale(LC_ALL, config_adv.locale);
119 	char *ctype = setlocale(LC_CTYPE, NULL);
120 	if( !ctype )
121 		return;
122 
123 	LocaleRec *localeRec;
124 	String localeDbName;
125 	localeDbName = DIR_RES;
126 	localeDbName += "LOCALE.RES";
127 	Database localeDbObj(localeDbName, 1);
128 	Database *dbLocale = &localeDbObj;
129 
130 	short locale_count = (short) dbLocale->rec_count();
131 
132 	//------ read in locale information -------//
133 
134 	int i;
135 	for( i=0 ; i<locale_count ; i++ )
136 	{
137 		localeRec = (LocaleRec*) dbLocale->read(i+1);
138 
139 		misc.rtrim_fld( lang, localeRec->lang, localeRec->LANG_LEN );
140 		if( !misc.str_icmpx(ctype, lang) )
141 			continue;
142 
143 		misc.rtrim_fld( fontset, localeRec->fontset, localeRec->FONTSET_LEN );
144 		misc.rtrim_fld( codeset, localeRec->codeset, localeRec->CODESET_LEN );
145 		break;
146 	}
147 
148 	if( i >= locale_count )
149 	{
150 		strcpy(lang, "??");
151 		strcpy(codeset, "ISO-8859-1");
152 	}
153 
154 	String tocode(codeset);
155 	tocode += "//TRANSLIT";
156 
157 	if( cd != (iconv_t)-1 )
158 		iconv_close(cd);
159 	if( cd_latin != (iconv_t)-1 )
160 		iconv_close(cd_latin);
161 	cd = iconv_open(tocode, "");
162 	cd_latin = iconv_open("ISO-8859-1", "");
163 	cd_from_sdl = iconv_open("ISO-8859-1//TRANSLIT//IGNORE", "UTF-8");
164 #endif
165 }
166 //------------- End of function LocaleRes::change_locale ---------//
167 
168 
169 #ifdef ENABLE_NLS
170 #define BUF_INCR 1000
conv_str(iconv_t cd,const char * s)171 const char *LocaleRes::conv_str(iconv_t cd, const char *s)
172 {
173 	if( cd == (iconv_t)-1 )
174 		return s;
175 
176 	size_t in_left;
177 	size_t out_left;
178 	char *p1 = in_buf;
179 	char *p2 = out_buf;
180 
181 	in_left = strlen(s);
182 	if( in_left > in_buf_size )
183 	{
184 		in_buf_size = in_left;
185 		in_buf = mem_resize(in_buf, in_buf_size+1);
186 	}
187 	strncpy(in_buf, s, in_left);
188 	in_buf[in_left] = 0;
189 	out_left = out_buf_size;
190 
191 	size_t c;
192 	while( in_left>0 )
193 	{
194 		c = iconv(cd, &p1, &in_left, &p2, &out_left);
195 		if( c == (size_t)-1 )
196 			return s;
197 		if( in_left )
198 		{
199 			out_left += BUF_INCR;
200 			out_buf_size += BUF_INCR;
201 			out_buf = mem_resize(out_buf, out_buf_size+1);
202 		}
203 	}
204 	out_buf[out_buf_size-out_left] = 0;
205 
206 	return out_buf;
207 }
208 #endif
209