*_list files, allow words in all-capitals which imply $allcaps attribute. Voices: Look for voices also in espeak-data/voices/test. lang=eo: Adjust syllable lengths. Use break between word (word_gap=1). wave.cpp: Fixes to copyBuffer(), wave_write(). git-svn-id: https://espeak.svn.sourceforge.net/svnroot/espeak/trunk@201 d46cf337-b52f-0410-862d-fd96e6ae7743master
@@ -510,7 +510,7 @@ | |||
buiten (ste bYyt@n // restore default stress: buitenste/-s | |||
buiten (t bYyt@n // restore default stress: buitentoe/buitentyds | |||
buiten bYyt@n' // buitendien/buitensporig | |||
buite b'Yyt@ // buitelandse/buitestander/buitew�eld | |||
buite bYyt@ // buitelandse/buitestander/buitewêreld/trekkerbuiteband | |||
bul (ga b%ul // fix stress and u sound: Bulgaarse/Bulgare | |||
bulle (tin b%ul@ // fix stress and u sound: bulletin and compounds | |||
bur (lesk b%Wr // move default stress: burlesk/-e | |||
@@ -905,7 +905,7 @@ | |||
CAnn) e (CA @ // banneling/sinnebeeld/spinnekop/-rak | |||
ies) e (b @ // fix e sound: dinamiesebinding/ekonomiesebemagtiging | |||
&At) e (be@ @ // fix e sound: batebestuur/sekuriteitebeurs/soldateberoep, etc. | |||
&At) e (bA@ @ // fix e sound: batebestuur/sekuriteitebeurs/soldatebbaadjie/geslotebaan, etc. | |||
Aw) e (bA @ // fix e sound: briewebesteller/diewebende/newebedoeling/skewebek/stywebeen | |||
@C) e (bo @ // compounds with boek/boer/boog/boom/bol/bord/borsel/bos/ grondbonebotter/kamdebo... | |||
@C) e (bu @ // briewebus/ereburger/novellebundel/urinebuis/woedebui | |||
@@ -3347,6 +3347,7 @@ | |||
prakti (syn pr%akt%i // move default stress: praktisien and compounds and plural | |||
_) prak (tyk pr%ak // stress: praktyk and compounds | |||
prefek prifEk // fix vowel sounds: prefek/-te/-tuur and compounds | |||
pre (histo pre@ // fix pre sound: prehistories/-e | |||
pre (lud pr@ // fix stress and e sound: prelude/-s/(ge)preludeer | |||
pre (mier pr@ // move default stress and fix e sound: premier and compounds | |||
pre (nata pr,e@ // fix e sound: prenataal/-tale | |||
@@ -3379,6 +3380,7 @@ | |||
proble (mati pr%Obl@ // fix vowel sounds: problematies/-e/problematiek | |||
profesie prOf@s'i // fix vowel sounds and move stress | |||
profit (e pr%Of@t // fix stress and vowel sounds: profiteer/-tering | |||
progester (o pr%o@x2%Est@r // fix e sound: progesteroon(-aanvulling/-behandeling/-tekort) | |||
pro (gram pr%u // fix stress and o sound: program/-e/ontwikkelingsprogram | |||
programme (ring pr%ux2r%ame@ // fix e sound and stress: (rekenaar)programmering(staal), etc. | |||
pro (gress pr%o@ // fix stress and o sound: progressie/-f/-we | |||
@@ -3685,6 +3687,7 @@ | |||
sekwe (strA s%Ekw@ // fix e sounds: sekwestrasie/sekwestreer and compounds | |||
bloed) se (l s& // fix e sound: (wit)bloedsel(le)(telling and similar compounds | |||
heuning) se (lK s& // fix e sound: heuningsel/-le | |||
liggaam) se (lK s& // fix e sound: liggaamsel/-le | |||
sela (kant s%e@l@ // fix stress and vowel sounds: selakant/-e | |||
selder (y s%&ld@r // move default stress: seldery and compounds | |||
&) sele (_ s'e@l@ | |||
@@ -3912,6 +3915,7 @@ | |||
staties st'A:tis | |||
sta (tutA st%a // fix stress and a sound: statute/statutêr | |||
steding ste@d@N // besteding and compounds | |||
ste (ke_ ste@ // fix e sound: by-/mes-/proefsteke | |||
C) steker ste@k@r // e sound: (aan/dop/kwaad/rugsteker/-s/-y, etc. | |||
_ne) stel st@l // fix e sound: nestel/-end | |||
wor) stel st@l //worstel e sound in compounds |
@@ -395,6 +395,8 @@ | |||
_) erob (er %E*o:b | |||
@) esen (_ e:z@n | |||
@) ett (_ 'Et | |||
eum (_ 'e:Um | |||
@@) eum (_ =e:Um | |||
@) eur (_ 'Y:* | |||
euse (_ 'Y:z@ | |||
eusen (_ 'Y:z@n | |||
@@ -558,7 +560,7 @@ | |||
_) i (llu %I | |||
_) i (mag I | |||
r) i (na_ 'i: | |||
@) ing (_N _^_EN | |||
// @) ing (_N _^_EN | |||
_) in (k %In | |||
_) inter Int@* | |||
&) in (_ i2n |
@@ -532,3 +532,16 @@ u W y | |||
** b d dZ f g h j | |||
k l m n p R3 s S | |||
t tS ts v x z Z | |||
Dictionary kn_dict | |||
a a: aI aU e E e: i | |||
I i: o o: r- u u: V | |||
y | |||
: b c ch d d. dZ f | |||
g h j J k kh l l. | |||
m n N n. n^ p ph R | |||
R2 s s. S; t t. t.h th | |||
tS v w z |
@@ -1,4 +1,4 @@ | |||
57 phoneme tables | |||
58 phoneme tables | |||
new total | |||
base 101 101 | |||
base2 24 120 | |||
@@ -52,10 +52,11 @@ | |||
da 15 131 | |||
sq 23 129 | |||
ml 13 141 | |||
kn 15 141 | |||
bn 59 147 | |||
ne 23 151 | |||
lv 28 123 | |||
hy 16 114 | |||
hy 17 115 | |||
om 18 118 | |||
Data file Used by | |||
@@ -597,6 +598,8 @@ r3/r_trill.wav [R2] base | |||
[x] pt | |||
[R2] lv | |||
r3/r_u [(u)] base | |||
r3/r_ulv [r"] hy | |||
r3/r_uvl [r"] hy | |||
r3/rx [*] base | |||
[r/] base | |||
[r/] af | |||
@@ -1100,6 +1103,7 @@ vdiph/aau_2 [aU] en_wi | |||
[aU] la | |||
[aau] zhy | |||
vdiph/aau_3 [aU] hi | |||
[aU] kn | |||
[aU] bn | |||
[aU] ne | |||
vdiph/aau_4 [aU] vi | |||
@@ -1115,6 +1119,7 @@ vdiph/ai [aI] base2 | |||
[aI] pt | |||
[a:I] vi | |||
[aI] id | |||
[aI] kn | |||
[aI] hy | |||
vdiph/ai_2 [aI] cy | |||
[aY] cy | |||
@@ -1402,6 +1407,7 @@ vowel/@ [@] base | |||
[V] cy | |||
[@4] hi | |||
[@] ml | |||
[@] kn | |||
[@4] bn | |||
[@] hy | |||
vowel/@- [@-] base | |||
@@ -1412,6 +1418,8 @@ vowel/& [a] en_rp | |||
[&] sv | |||
[&] bn | |||
[&:] bn | |||
[&] lv | |||
[&:] lv | |||
vowel/0 [0] en | |||
[O] hi | |||
[O] pt | |||
@@ -1493,6 +1501,7 @@ vowel/a#_2 [a#] pl | |||
[&] is | |||
[a/] sw | |||
[a/] sq | |||
[a] kn | |||
vowel/a_3 [a] en_sc | |||
[a/] en_sc | |||
[A:] en_sc | |||
@@ -1527,6 +1536,7 @@ vowel/a_5 [a:] ta | |||
[a] tr | |||
[a] sq | |||
[a:] ml | |||
[a:] kn | |||
vowel/a_6 [a] fr | |||
[a2] fr | |||
vowel/aa [a] fi | |||
@@ -1570,6 +1580,7 @@ vowel/@_bck [@] hi | |||
[@/] hi | |||
[@] zh | |||
[@] bn | |||
[V] ne | |||
[@/] ne | |||
vowel/e [e] base2 | |||
[e:] en | |||
@@ -1598,6 +1609,7 @@ vowel/e [e] base2 | |||
[e] da | |||
[e] ml | |||
[e:] ml | |||
[e:] kn | |||
[e] ne | |||
vowel/e# [I] en_sc | |||
[I2] en_sc | |||
@@ -1644,8 +1656,6 @@ vowel/ee_3 [&] af | |||
vowel/ee_6 [&] sk | |||
[E3] sv | |||
[E] ku | |||
[&] lv | |||
[&:] lv | |||
vowel/e_mid [E] en_rp | |||
[e] jbo | |||
[E] fr | |||
@@ -1667,7 +1677,6 @@ vowel/e_mid [E] en_rp | |||
[E2] id | |||
[E] da | |||
[E] bn | |||
[e] lv | |||
[e] hy | |||
vowel/e_mid2 [E] af | |||
[E] de | |||
@@ -1682,6 +1691,8 @@ vowel/e_mid2 [E] af | |||
[e] sw | |||
[e] tr | |||
[E] ko | |||
[e] kn | |||
[e] lv | |||
[e:] lv | |||
[E] om | |||
vowel/@_fnt [@] en_wi | |||
@@ -1713,6 +1724,7 @@ vowel/i [i] base2 | |||
[i#] rw | |||
[i] ko | |||
[i:] ml | |||
[i:] kn | |||
[i] ne | |||
[i] hy | |||
[i:] om | |||
@@ -1726,7 +1738,6 @@ vowel/i_3 [i] af | |||
[i] fr | |||
[i:] fr | |||
[i:] sk | |||
[i] lv | |||
[i:] lv | |||
vowel/i_4 [i] fi | |||
[i] hu | |||
@@ -1743,6 +1754,8 @@ vowel/i_6 [i] ta | |||
[i] ku | |||
[i] id | |||
[i] ml | |||
[i] kn | |||
[i] lv | |||
vowel/i#_6 [i.] zh | |||
vowel/i_7 [i] pl | |||
vowel/i#_7 [i[] zh | |||
@@ -1774,6 +1787,7 @@ vowel/ii# [Y] cy | |||
[i] sq | |||
[e#] sq | |||
[y] ml | |||
[y] kn | |||
vowel/ii_2 [i] zh | |||
vowel/ii#_2 [y] pl | |||
vowel/ii_3 [I] cy | |||
@@ -1839,6 +1853,8 @@ vowel/o [o] base2 | |||
[o#] rw | |||
[o] ml | |||
[o:] ml | |||
[o] kn | |||
[o:] kn | |||
[o] bn | |||
[o] hy | |||
vowel/o_2 [o:] cy | |||
@@ -1952,6 +1968,8 @@ vowel/u [u:] en_wi | |||
[u] id | |||
[u] ml | |||
[u:] ml | |||
[u] kn | |||
[u:] kn | |||
[u] bn | |||
[u:] om | |||
vowel/u# [u:] en_sc | |||
@@ -2026,7 +2044,6 @@ vowel/uu_bck [U] en_wi | |||
[U] om | |||
vowel/u_unr [u-] ko | |||
vowel/V [3] en_sc | |||
[V] ne | |||
vowel/V_2 [V] en | |||
[a] af | |||
[V] ru |
@@ -20,7 +20,7 @@ endphoneme | |||
phoneme i | |||
vowel starttype (i) endtype (i) | |||
length 160 | |||
length 170 | |||
formants vowel/i | |||
linkout ; | |||
endphoneme | |||
@@ -42,42 +42,42 @@ endphoneme | |||
phoneme aU | |||
vowel starttype (a) endtype (u) | |||
length 240 | |||
length 230 | |||
formants vdiph/au_4 | |||
endphoneme | |||
phoneme eU | |||
vowel starttype (e) endtype (u) | |||
length 240 | |||
length 230 | |||
formants vdiph/eu | |||
endphoneme | |||
phoneme aI | |||
vowel starttype (a) endtype (i) | |||
length 260 | |||
length 240 | |||
formants vdiph/ai | |||
endphoneme | |||
phoneme eI | |||
vowel starttype (e) endtype (i) | |||
length 250 | |||
length 230 | |||
formants vdiph/eei_2 | |||
endphoneme | |||
phoneme OI | |||
vowel starttype (o) endtype (i) | |||
length 260 | |||
length 240 | |||
formants vdiph/ooi | |||
endphoneme | |||
phoneme uI | |||
vowel starttype (u) endtype (i) | |||
length 250 | |||
length 230 | |||
formants vdiph/ui | |||
endphoneme | |||
@@ -1324,6 +1324,9 @@ include ph_albanian | |||
phonemetable ml hi | |||
include ph_malayalam | |||
phonemetable kn hi | |||
include ph_kannada | |||
phonemetable bn hi | |||
include ph_bengali | |||
@@ -602,7 +602,7 @@ int Compile::LoadSpect(const char *path, int control) | |||
float total; | |||
float pkheight; | |||
int marker1_set=0; | |||
int frame_vowelbreak; | |||
int frame_vowelbreak=NULL; | |||
SpectFrame *fr; | |||
wxString path_sep = _T("/"); | |||
@@ -186,6 +186,7 @@ int compile_line(char *linebuf, char *dict_line, int *hash) | |||
int len_phonetic; | |||
int text_not_phonemes; // this word specifies replacement text, not phonemes | |||
unsigned int wc; | |||
int all_upper_case; | |||
char *mnemptr; | |||
char *comment; | |||
@@ -430,11 +431,34 @@ static char nullstring[] = {0}; | |||
word[ix] = 0; | |||
} | |||
else | |||
if((word[0] & 0x80)==0) // 7 bit ascii only | |||
if(word[0] != '_') | |||
{ | |||
// If first letter is uppercase, convert to lower case. (Only if it's 7bit ascii) | |||
// ??? need to consider utf8 here | |||
word[0] = tolower(word[0]); | |||
// convert to lower case, and note if the word is all-capitals | |||
int c2; | |||
all_upper_case = 1; | |||
p = word; | |||
for(p=word;;) | |||
{ | |||
// this assumes that the lower case char is the same length as the upper case char | |||
// OK, except for Turkish "I", but use towlower() rather than towlower2() | |||
ix = utf8_in(&c2,p,0); | |||
if(c2 == 0) | |||
break; | |||
if(iswupper(c2)) | |||
{ | |||
utf8_out(towlower(c2),p); | |||
} | |||
else | |||
{ | |||
all_upper_case = 0; | |||
} | |||
p += ix; | |||
} | |||
if(all_upper_case) | |||
{ | |||
flag_codes[n_flag_codes++] = BITNUM_FLAG_ALLCAPS; | |||
} | |||
} | |||
len_word = strlen(word); | |||
@@ -793,9 +817,12 @@ void copy_rule_string(char *string, int &state) | |||
} | |||
break; | |||
case '$': // obsolete, replaced by S | |||
fprintf(f_log,"%5d: $ now not allowed, use S for suffix",linenum); | |||
error_count++; | |||
break; | |||
case 'P': | |||
sxflags |= SUFX_P; // Prefix, now drop through to Suffix | |||
case '$': // obsolete, replaced by S | |||
case 'S': | |||
output[ix++] = RULE_ENDING; | |||
value = 0; |
@@ -1768,6 +1768,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
int distance_left; | |||
int lg_pts; | |||
int n_bytes; | |||
int add_points; | |||
MatchRecord match; | |||
static MatchRecord best; | |||
@@ -1885,6 +1886,8 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
continue; | |||
} | |||
add_points = 0; | |||
switch(match_type) | |||
{ | |||
case 0: | |||
@@ -1894,7 +1897,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
if((letter == rb) || ((letter==(unsigned char)REPLACED_E) && (rb=='e'))) | |||
{ | |||
match.points += 21; | |||
add_points = 21; | |||
consumed++; | |||
} | |||
else | |||
@@ -1920,7 +1923,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
lg_pts = 20; | |||
if(letter_group==2) | |||
lg_pts = 19; // fewer points for C, general consonant | |||
match.points += (lg_pts-distance_right); | |||
add_points = (lg_pts-distance_right); | |||
post_ptr += letter_xbytes; | |||
} | |||
else | |||
@@ -1931,7 +1934,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
letter_group = *rule++ - 'A'; | |||
if((n_bytes = IsLetterGroup(post_ptr-1,letter_group,0)) >0) | |||
{ | |||
match.points += (20-distance_right); | |||
add_points = (20-distance_right); | |||
post_ptr += (n_bytes-1); | |||
} | |||
else | |||
@@ -1941,7 +1944,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
case RULE_NOTVOWEL: | |||
if(!IsLetter(letter_w,0)) | |||
{ | |||
match.points += (20-distance_right); | |||
add_points = (20-distance_right); | |||
post_ptr += letter_xbytes; | |||
} | |||
else | |||
@@ -1951,14 +1954,14 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
case RULE_DIGIT: | |||
if(IsDigit(letter_w)) | |||
{ | |||
match.points += (20-distance_right); | |||
add_points = (20-distance_right); | |||
post_ptr += letter_xbytes; | |||
} | |||
else | |||
if(langopts.tone_numbers) | |||
{ | |||
// also match if there is no digit | |||
match.points += (20-distance_right); | |||
add_points = (20-distance_right); | |||
post_ptr--; | |||
} | |||
else | |||
@@ -1968,7 +1971,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
case RULE_NONALPHA: | |||
if(!iswalpha(letter_w)) | |||
{ | |||
match.points += (21-distance_right); | |||
add_points = (21-distance_right); | |||
post_ptr += letter_xbytes; | |||
} | |||
else | |||
@@ -1977,14 +1980,14 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
case RULE_DOUBLE: | |||
if(letter == last_letter) | |||
match.points += (21-distance_right); | |||
add_points = (21-distance_right); | |||
else | |||
failed = 1; | |||
break; | |||
case RULE_ALT1: | |||
if(dict_flags & FLAG_ALT_TRANS) | |||
match.points++; | |||
add_points = 1; | |||
else | |||
failed = 1; | |||
break; | |||
@@ -1992,7 +1995,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
case '-': | |||
if((letter == '-') || ((letter == ' ') && (word_flags & FLAG_HYPHEN_AFTER))) | |||
{ | |||
match.points += (22-distance_right); // one point more than match against space | |||
add_points = (22-distance_right); // one point more than match against space | |||
} | |||
else | |||
failed = 1; | |||
@@ -2021,7 +2024,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
p += utf8_in(&letter_w,p,0); | |||
} | |||
if(syllable_count <= 0) | |||
match.points+= (19-distance_right); | |||
add_points = (19-distance_right); | |||
else | |||
failed = 1; | |||
} | |||
@@ -2040,12 +2043,12 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
p += utf8_in(&letter_w,p,0); | |||
} | |||
if(!failed) | |||
match.points += (19-distance_right); | |||
add_points = (19-distance_right); | |||
} | |||
break; | |||
case RULE_INC_SCORE: | |||
match.points += 20; // force an increase in points | |||
add_points = 20; // force an increase in points | |||
break; | |||
case RULE_DEL_FWD: | |||
@@ -2070,16 +2073,16 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
if(word_flags & FLAG_SUFFIX_REMOVED) | |||
failed = 1; // a suffix has been removed | |||
else | |||
match.points++; | |||
add_points = 1; | |||
break; | |||
default: | |||
if(letter == rb) | |||
{ | |||
if(letter == RULE_SPACE) | |||
match.points += (21-distance_right); | |||
add_points = (21-distance_right); | |||
else | |||
match.points += (21-distance_right); | |||
add_points = (21-distance_right); | |||
} | |||
else | |||
failed = 1; | |||
@@ -2108,7 +2111,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
lg_pts = 20; | |||
if(letter_group==2) | |||
lg_pts = 19; // fewer points for C, general consonant | |||
match.points += (lg_pts-distance_left); | |||
add_points = (lg_pts-distance_left); | |||
pre_ptr -= letter_xbytes; | |||
} | |||
else | |||
@@ -2119,7 +2122,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
letter_group = *rule++ - 'A'; | |||
if((n_bytes = IsLetterGroup(pre_ptr-letter_xbytes,letter_group,1)) >0) | |||
{ | |||
match.points += (20-distance_right); | |||
add_points = (20-distance_right); | |||
pre_ptr -= (n_bytes-1); | |||
} | |||
else | |||
@@ -2129,7 +2132,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
case RULE_NOTVOWEL: | |||
if(!IsLetter(letter_w,0)) | |||
{ | |||
match.points += (20-distance_left); | |||
add_points = (20-distance_left); | |||
pre_ptr -= letter_xbytes; | |||
} | |||
else | |||
@@ -2138,7 +2141,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
case RULE_DOUBLE: | |||
if(letter == last_letter) | |||
match.points += (21-distance_left); | |||
add_points = (21-distance_left); | |||
else | |||
failed = 1; | |||
break; | |||
@@ -2146,7 +2149,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
case RULE_DIGIT: | |||
if(IsDigit(letter_w)) | |||
{ | |||
match.points += (21-distance_left); | |||
add_points = (21-distance_left); | |||
pre_ptr -= letter_xbytes; | |||
} | |||
else | |||
@@ -2156,7 +2159,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
case RULE_NONALPHA: | |||
if(!iswalpha(letter_w)) | |||
{ | |||
match.points += (21-distance_right); | |||
add_points = (21-distance_right); | |||
pre_ptr -= letter_xbytes; | |||
} | |||
else | |||
@@ -2172,14 +2175,14 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
syllable_count++; /* number of syllables to match */ | |||
} | |||
if(syllable_count <= word_vowel_count) | |||
match.points+= (19-distance_left); | |||
add_points = (19-distance_left); | |||
else | |||
failed = 1; | |||
break; | |||
case RULE_STRESSED: | |||
if(word_stressed_count > 0) | |||
match.points += 19; | |||
add_points = 19; | |||
else | |||
failed = 1; | |||
break; | |||
@@ -2197,20 +2200,20 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
p -= utf8_in(&letter_w,p,1); | |||
} | |||
if(!failed) | |||
match.points += 3; | |||
add_points = 3; | |||
} | |||
break; | |||
case RULE_IFVERB: | |||
if(expect_verb) | |||
match.points += 1; | |||
add_points = 1; | |||
else | |||
failed = 1; | |||
break; | |||
case RULE_CAPITAL: | |||
if(word_flags & FLAG_FIRST_UPPER) | |||
match.points += 1; | |||
add_points = 1; | |||
else | |||
failed = 1; | |||
break; | |||
@@ -2221,7 +2224,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
{ | |||
if(*p == '.') | |||
{ | |||
match.points +=50; | |||
add_points = 50; | |||
break; | |||
} | |||
} | |||
@@ -2232,7 +2235,7 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
case '-': | |||
if((letter == '-') || ((letter == ' ') && (word_flags & FLAG_HYPHEN))) | |||
{ | |||
match.points += (22-distance_right); // one point more than match against space | |||
add_points = (22-distance_right); // one point more than match against space | |||
} | |||
else | |||
failed = 1; | |||
@@ -2242,9 +2245,9 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
if(letter == rb) | |||
{ | |||
if(letter == RULE_SPACE) | |||
match.points += 4; | |||
add_points = 4; | |||
else | |||
match.points += (21-distance_left); | |||
add_points = (21-distance_left); | |||
} | |||
else | |||
failed = 1; | |||
@@ -2252,6 +2255,9 @@ void Translator::MatchRule(char *word[], const char *group, char *rule, MatchRec | |||
} | |||
break; | |||
} | |||
if(failed == 0) | |||
match.points += add_points; | |||
} | |||
if(failed == 2) |
@@ -487,6 +487,14 @@ void Translator::CalcLengths() | |||
} | |||
// calc length modifier | |||
if(next->ph->code == phonPAUSE_VSHORT) | |||
{ | |||
// ignore very short pause | |||
next = next2; | |||
next2 = next3; | |||
next3 = &phoneme_list[ix+4]; | |||
} | |||
if(more_syllables==0) | |||
{ | |||
len = langopts.length_mods0[next2->ph->length_mod *10+ next->ph->length_mod]; |
@@ -35,7 +35,7 @@ | |||
#include "translate.h" | |||
#include "wave.h" | |||
const char *version_string = "1.39.18 06.Nov.08"; | |||
const char *version_string = "1.39.22 10.Nov.08"; | |||
const int version_phdata = 0x013900; | |||
int option_device_number = -1; |
@@ -49,6 +49,7 @@ | |||
#define OFFSET_DEVANAGARI 0x900 | |||
#define OFFSET_BENGALI 0x980 | |||
#define OFFSET_TAMIL 0xb80 | |||
#define OFFSET_KANNADA 0xc80 | |||
#define OFFSET_MALAYALAM 0xd00 | |||
#define OFFSET_KOREAN 0x1100 | |||
@@ -274,7 +275,7 @@ Translator *SelectTranslator(const char *name) | |||
case L('e','o'): | |||
{ | |||
static const short stress_lengths_eo[8] = {145, 180, 200, 190, 0, 0, 300, 320}; | |||
static const short stress_lengths_eo[8] = {145, 145, 200, 170, 0, 0, 320, 340}; | |||
static const unsigned char stress_amps_eo[] = {16,14, 20,20, 20,24, 24,22 }; | |||
static const wchar_t eo_char_apostrophe[2] = {'l',0}; | |||
@@ -284,10 +285,10 @@ Translator *SelectTranslator(const char *name) | |||
tr->charset_a0 = charsets[3]; // ISO-8859-3 | |||
tr->char_plus_apostrophe = eo_char_apostrophe; | |||
tr->langopts.vowel_pause = 1; | |||
tr->langopts.word_gap = 1; | |||
tr->langopts.stress_rule = 2; | |||
tr->langopts.stress_flags = 0x6 | 0x10; | |||
tr->langopts.unstressed_wd1 = 1; | |||
tr->langopts.unstressed_wd1 = 3; | |||
tr->langopts.unstressed_wd2 = 2; | |||
tr->langopts.numbers = 0x1409 + NUM_ROMAN; | |||
@@ -434,17 +435,19 @@ SetLengthMods(tr,3); // all equal | |||
case L('h','y'): // Armenian | |||
{ | |||
static const short stress_lengths_hy[8] = {250, 200, 250, 250, 0, 0, 250, 250}; | |||
static const char hy_vowels[] = {0x31, 0x35, 0x37, 0x38, 0x3b, 0x48, 0x55, 0}; | |||
static const char hy_consonants[] = {0x32,0x33,0x34,0x36,0x39,0x3a,0x3c,0x3d,0x3e,0x3f, | |||
0x40,0x41,0x42,0x43,0x44,0x45,0x46,0x47,0x49,0x4a,0x4b,0x4c,0x4d,0x4e,0x4f,0x50,0x51,0x52,0x53,0x54,0x56,0}; | |||
tr = new Translator(); | |||
SetupTranslator(tr,stress_lengths_hy,NULL); | |||
tr->langopts.stress_rule = 3; // default stress on final syllable | |||
tr->letter_bits_offset = OFFSET_ARMENIAN; | |||
memset(tr->letter_bits,0,sizeof(tr->letter_bits)); | |||
SetLetterBits(tr,LETTERGP_A,hy_vowels); | |||
SetLetterBits(tr,LETTERGP_C,hy_consonants); | |||
tr->langopts.max_initial_consonants = 4; | |||
tr->langopts.max_initial_consonants = 6; | |||
} | |||
break; | |||
@@ -783,6 +786,7 @@ SetLengthMods(tr,3); // all equal | |||
case L('t','a'): // Tamil | |||
case L('m','l'): // Malayalam | |||
case L('k','n'): // Kannada | |||
{ | |||
static const short stress_lengths_ta[8] = {200, 200, 210, 210, 0, 0, 230, 230}; | |||
static const unsigned char stress_amps_ta[8] = {18,18, 18,18, 20,20, 22,22 }; | |||
@@ -799,6 +803,11 @@ SetLengthMods(tr,3); // all equal | |||
{ | |||
tr->letter_bits_offset = OFFSET_MALAYALAM; | |||
} | |||
else | |||
if(name2 == L('k','n')) | |||
{ | |||
tr->letter_bits_offset = OFFSET_KANNADA; | |||
} | |||
tr->langopts.param[LOPT_WORD_MERGE] = 1; // don't break vowels betwen words | |||
SetIndicLetters(tr); // call this after setting OFFSET_ | |||
} |
@@ -75,6 +75,7 @@ | |||
#define FLAG_VERB_EXT 0x100 /* extend the 'verb follows' */ | |||
#define FLAG_CAPITAL 0x200 /* pronunciation if initial letter is upper case */ | |||
#define FLAG_ALLCAPS 0x400 // only if the word is all capitals | |||
#define BITNUM_FLAG_ALLCAPS 0x2a | |||
#define FLAG_ACCENT 0x800 // character name is base-character name + accent name | |||
#define FLAG_HYPHENATED 0x1000 // multiple-words, but needs hyphen between parts 1 and 2 | |||
#define BITNUM_FLAG_HYPHENATED 0x2c |
@@ -547,6 +547,12 @@ voice_t *LoadVoice(const char *vname, int control) | |||
langname[1] = voicename[1]; | |||
langname[2] = 0; | |||
sprintf(buf,"%s%s%c%s",path_voices,langname,PATHSEP,voicename); | |||
if(GetFileLength(buf) <= 0) | |||
{ | |||
// look in "test" sub-directory | |||
sprintf(buf,"%stest%c%s",path_voices,PATHSEP,voicename); | |||
} | |||
} | |||
} | |||
@@ -652,29 +652,40 @@ void* wave_open(const char* the_api) | |||
//> | |||
//<copyBuffer | |||
static size_t copyBuffer(char* dest, char* src, size_t theSizeInBytes) | |||
{ | |||
size_t bytes_written=0; | |||
if(out_channels==1) | |||
{ | |||
SHOW("copyBuffer > memcpy %x (%d bytes)\n", (int)myWrite, theSizeInBytes); | |||
memcpy(dest, src, theSizeInBytes); | |||
bytes_written = theSizeInBytes; | |||
} | |||
else | |||
{ | |||
SHOW("copyBuffer > memcpy %x (%d bytes)\n", (int)myWrite, 2*theSizeInBytes); | |||
unsigned int i; | |||
uint16_t* a_dest = (uint16_t*)dest; | |||
uint16_t* a_src = (uint16_t*)src; | |||
for(i=0; i<theSizeInBytes/2; i++) | |||
{ | |||
a_dest[2*i] = a_src[i]; | |||
a_dest[2*i + 1] = a_src[i]; | |||
} | |||
bytes_written = 2*theSizeInBytes; | |||
} | |||
return bytes_written; | |||
static size_t copyBuffer(char* dest, char* src, const size_t theSizeInBytes) | |||
{ | |||
size_t bytes_written = 0; | |||
unsigned int i = 0; | |||
uint16_t* a_dest = NULL; | |||
uint16_t* a_src = NULL; | |||
if ((src != NULL) && dest != NULL) | |||
{ | |||
// copy for one channel (mono)? | |||
if(out_channels==1) | |||
{ | |||
SHOW("copyBuffer > 1 channel > memcpy %x (%d bytes)\n", (int)myWrite, theSizeInBytes); | |||
memcpy(dest, src, theSizeInBytes); | |||
bytes_written = theSizeInBytes; | |||
} | |||
else // copy for 2 channels (stereo) | |||
{ | |||
SHOW("copyBuffer > 2 channels > memcpy %x (%d bytes)\n", (int)myWrite, theSizeInBytes); | |||
i = 0; | |||
a_dest = (uint16_t* )dest; | |||
a_src = (uint16_t* )src; | |||
for(i=0; i<theSizeInBytes/2; i++) | |||
{ | |||
a_dest[2*i] = a_src[i]; | |||
a_dest[2*i+1] = a_src[i]; | |||
} | |||
bytes_written = 2*theSizeInBytes; | |||
} // end if(out_channels==1) | |||
} // end if ((src != NULL) && dest != NULL) | |||
return bytes_written; | |||
} | |||
//> | |||
@@ -682,107 +693,125 @@ static size_t copyBuffer(char* dest, char* src, size_t theSizeInBytes) | |||
size_t wave_write(void* theHandler, char* theMono16BitsWaveBuffer, size_t theSize) | |||
{ | |||
ENTER("wave_write"); | |||
size_t bytes_written = 0; | |||
size_t bytes_to_write = (out_channels==1) ? theSize : theSize*2; | |||
my_stream_could_start = 0; | |||
if(pa_stream == NULL) | |||
{ | |||
SHOW_TIME("wave_write > wave_open_sound\n"); | |||
if (0 != wave_open_sound()) | |||
ENTER("wave_write"); | |||
size_t bytes_written = 0; | |||
// space in ringbuffer for the sample needed: 1x mono channel but 2x for 1 stereo channel | |||
size_t bytes_to_write = (out_channels==1) ? theSize : theSize*2; | |||
my_stream_could_start = 0; | |||
if(pa_stream == NULL) | |||
{ | |||
SHOW_TIME("wave_write > wave_open_sound fails!"); | |||
return 0; | |||
} | |||
my_stream_could_start=1; | |||
} | |||
else if (!wave_is_busy(NULL)) | |||
{ | |||
my_stream_could_start = 1; | |||
} | |||
assert(BUFFER_LENGTH >= bytes_to_write); | |||
if (myWrite >= myBuffer + BUFFER_LENGTH) | |||
{ | |||
myWrite = myBuffer; | |||
} | |||
size_t aTotalFreeMem=0; | |||
char* aRead = myRead; | |||
SHOW("wave_write > aRead=%x, myWrite=%x\n", (int)aRead, (int)myWrite); | |||
while (1) | |||
{ | |||
if (my_callback_is_output_enabled | |||
&& (0==my_callback_is_output_enabled())) | |||
{ | |||
SHOW_TIME("wave_write > my_callback_is_output_enabled: no!"); | |||
return 0; | |||
SHOW_TIME("wave_write > wave_open_sound\n"); | |||
if (0 != wave_open_sound()) | |||
{ | |||
SHOW_TIME("wave_write > wave_open_sound fails!"); | |||
return 0; | |||
} | |||
my_stream_could_start=1; | |||
} | |||
aRead = myRead; | |||
if (myWrite >= aRead) | |||
else if (!wave_is_busy(NULL)) | |||
{ | |||
aTotalFreeMem = aRead + BUFFER_LENGTH - myWrite; | |||
my_stream_could_start = 1; | |||
} | |||
else | |||
assert(BUFFER_LENGTH >= bytes_to_write); | |||
if (myWrite >= myBuffer + BUFFER_LENGTH) | |||
{ | |||
aTotalFreeMem = aRead - myWrite; | |||
} | |||
if (aTotalFreeMem>1) | |||
myWrite = myBuffer; | |||
} // end if (myWrite >= myBuffer + BUFFER_LENGTH) | |||
size_t aTotalFreeMem=0; | |||
char* aRead = myRead; | |||
SHOW("wave_write > aRead=%x, myWrite=%x\n", (int)aRead, (int)myWrite); | |||
while (1) | |||
{ | |||
// -1 because myWrite must be different of aRead | |||
// otherwise buffer would be considered as empty | |||
aTotalFreeMem -= 1; | |||
} | |||
if (aTotalFreeMem >= bytes_to_write) | |||
if (my_callback_is_output_enabled && (0==my_callback_is_output_enabled())) | |||
{ | |||
SHOW_TIME("wave_write > my_callback_is_output_enabled: no!"); | |||
return 0; | |||
} | |||
aRead = myRead; | |||
// write pointer is before read pointer? | |||
if (myWrite >= aRead) | |||
{ | |||
aTotalFreeMem = aRead + BUFFER_LENGTH - myWrite; | |||
} | |||
else // read pointer is before write pointer! | |||
{ | |||
aTotalFreeMem = aRead - myWrite; | |||
} // end if (myWrite >= aRead) | |||
if (aTotalFreeMem>1) | |||
{ | |||
// -1 because myWrite must be different of aRead | |||
// otherwise buffer would be considered as empty | |||
aTotalFreeMem -= 1; | |||
} // end if (aTotalFreeMem>1) | |||
if (aTotalFreeMem >= bytes_to_write) | |||
{ | |||
break; | |||
} // end if (aTotalFreeMem >= bytes_to_write) | |||
//SHOW_TIME("wave_write > wait"); | |||
SHOW("wave_write > wait: aTotalFreeMem=%d\n", aTotalFreeMem); | |||
SHOW("wave_write > aRead=%x, myWrite=%x\n", (int)aRead, (int)myWrite); | |||
usleep(10000); | |||
} // end while (1) | |||
aRead = myRead; | |||
// write pointer is ahead the read pointer? | |||
if (myWrite >= aRead) | |||
{ | |||
break; | |||
} | |||
// SHOW_TIME("wave_write > wait"); | |||
SHOW("wave_write > wait: aTotalFreeMem=%d\n", aTotalFreeMem); | |||
SHOW("wave_write > aRead=%x, myWrite=%x\n", (int)aRead, (int)myWrite); | |||
usleep(10000); | |||
} | |||
aRead = myRead; | |||
if (myWrite >= aRead) | |||
{ | |||
SHOW_TIME("wave_write > myWrite > aRead"); | |||
size_t aFreeMem = myBuffer + BUFFER_LENGTH - myWrite; | |||
if (aFreeMem >= bytes_to_write) | |||
SHOW_TIME("wave_write > myWrite >= aRead"); | |||
// determine remaining free memory to the end of the ringbuffer | |||
size_t aFreeMem = myBuffer + BUFFER_LENGTH - myWrite; | |||
// is enough linear space available (regardless 1 or 2 channels)? | |||
if (aFreeMem >= bytes_to_write) | |||
{ | |||
// copy direct - no wrap around at end of ringbuffer needed | |||
myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer, theSize); | |||
} | |||
else // not enough linear space available | |||
{ | |||
// 2 channels (stereo)? | |||
if (out_channels == 2) | |||
{ | |||
// copy with wrap around at the end of ringbuffer | |||
const size_t bytes_written = copyBuffer(myWrite, theMono16BitsWaveBuffer, aFreeMem/2); | |||
myWrite = myBuffer; | |||
myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer+aFreeMem/2, theSize - aFreeMem/2); | |||
} | |||
else // 1 channel (mono) | |||
{ | |||
// copy with wrap around at the end of ringbuffer | |||
const size_t bytes_written = copyBuffer(myWrite, theMono16BitsWaveBuffer, aFreeMem); | |||
myWrite = myBuffer; | |||
myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer+aFreeMem, theSize - aFreeMem); | |||
} // end if (out_channels == 2) | |||
} // end if (aFreeMem >= bytes_to_write) | |||
} // if (myWrite >= aRead) | |||
else // read pointer is ahead the write pointer | |||
{ | |||
myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer, theSize); | |||
} | |||
else | |||
SHOW_TIME("wave_write > myWrite <= aRead"); | |||
myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer, theSize); | |||
} // end if (myWrite >= aRead) | |||
bytes_written = bytes_to_write; | |||
myWritePosition += theSize/sizeof(uint16_t); // add number of samples | |||
if (my_stream_could_start && (get_used_mem() >= out_channels * sizeof(uint16_t) * FRAMES_PER_BUFFER)) | |||
{ | |||
int bytes_written = copyBuffer(myWrite, theMono16BitsWaveBuffer, aFreeMem); | |||
myWrite = myBuffer; | |||
myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer+aFreeMem, bytes_to_write-bytes_written); | |||
} | |||
} | |||
else | |||
{ | |||
SHOW_TIME("wave_write > myWrite <= aRead"); | |||
myWrite += copyBuffer(myWrite, theMono16BitsWaveBuffer, theSize); | |||
} | |||
bytes_written = theSize; | |||
myWritePosition += theSize/sizeof(uint16_t); // add number of samples | |||
if (my_stream_could_start && (get_used_mem() >= out_channels * sizeof(uint16_t) * FRAMES_PER_BUFFER)) | |||
{ | |||
start_stream(); | |||
} | |||
SHOW_TIME("wave_write > LEAVE"); | |||
return bytes_written; | |||
start_stream(); | |||
} // end if (my_stream_could_start && (get_used_mem() >= out_channels * sizeof(uint16_t) * FRAMES_PER_BUFFER)) | |||
SHOW_TIME("wave_write > LEAVE"); | |||
return bytes_written; | |||
} | |||
//> |