Merge branch 'master' into build

Conflicts:
	src/Makefile.espeakedit
This commit is contained in:
Reece Dunn
2010-06-28 21:08:08 +01:00
92 changed files with 3437 additions and 2434 deletions
+36 -32
View File
@@ -111,9 +111,9 @@ _19 n'ed@-n
_2X t'y:w
_3X tR'&#Dv@ //PB [tR'ADv@] changed to [tR'&#Dv@]
_4X f'WRV //PB [f'W:*3] changed to [ f'WRV]
_5X hal't*es
_5X h&l't*es // PB [a] changed to [&]
_6X t*'es
_7X halfj'&rs
_7X h&lfj'&rs // PV a changed to &
_8X f'irs
_9X h&lf'Ems // PB a changed to &
_0C h'un*@:D
@@ -163,6 +163,8 @@ en e:n $u
et ed $u
her $u
kun $u
vel $u+
da $u
// conjunctions
og V $u+ $pause // and
@@ -187,6 +189,7 @@ med $u+ // with
af & // PB changed from [a?] to [&] - sound too short in a sentence
// Also removed $u from 'af' and other words. They disappeared.
ad &: // PB added 'ad'
ad &D $atend $sentence // PB "Det må ikke skille os ad."
at &: $u // PB changed from [at] to [&:]
hos // at - PB: removed [$u+]
som sVm // which / that - PB: removed [$u+]
@@ -257,7 +260,7 @@ f Ef
g ge:
h hO:
_i i:
j joD
j jVD // PB changed from [o]
k kO:
l El
m Em
@@ -316,7 +319,6 @@ interface _^_EN
image _^_EN
joke _^_EN
joystick _^_EN
junkie _^_EN
laptop _^_EN
level _^_EN
login _^_EN
@@ -335,13 +337,11 @@ password _^_EN
penthouse _^_EN
pickup _^_EN
pidgin _^_EN
producer _^_EN
ranger _^_EN
receiver _^_EN
research _^_EN
remake _^_EN
roadie _^_EN
roastbeef _^_EN
run _^_EN
scanner _^_EN
science _^_EN
@@ -356,7 +356,6 @@ small _^_EN
snob _^_EN
song _^_EN
source _^_EN
spam _^_EN
spirit _^_EN
squaw _^_EN
sweatshirt _^_EN
@@ -2344,7 +2343,7 @@ dessin des'EN $alt
dioxin $alt
disciplin $alt
doktrin $alt
(drive-in) drajv'in $alt
//(drive-in) drajv'in $alt
dusin $alt
endokrin $alt
endorfin $alt
@@ -2398,7 +2397,6 @@ lupin $alt
magasin $alt
mandarin $alt
mandolin $alt
mannequin m&n@k'EN $alt
margin $alt
marin $alt
marocain mAro'kEN $alt
@@ -5046,6 +5044,7 @@ adstringer $alt
adviser $alt
advoker $alt
afficer $alt
aflever $alt
afmarcher $alt
afrikaniser $alt
agere $alt
@@ -5154,7 +5153,7 @@ banaliser $alt
bandagere $alt
banderolere $alt
barbariser $alt
barber $alt
barbere $alt
barder $alt
barrier $alt
barrikader $alt
@@ -5179,7 +5178,7 @@ bonbonniere bVNbVNj'E:r $alt
boniter $alt
botaniser $alt
braiser $alt
briketter $alt
brikettere $alt
brillere $alt
brochere $alt
brodere $alt
@@ -5188,7 +5187,7 @@ bronzere $alt
brunere $alt
brutaliser $alt
bruyere bryj'E:r $alt
budgetter $alt
budgettere $alt
bugser $alt
bureaukratiser $alt
cadmier $alt
@@ -5274,7 +5273,7 @@ deputer $alt
dereguler $alt
deriver $alt
desarmer $alt
deserter $alt
desertere $alt
designere $alt
desinficer $alt
destiller $alt
@@ -5434,7 +5433,7 @@ farser $alt
fasciner $alt
favoriser $alt
feminiser $alt
ferier $alt
feriere $alt
fermenter $alt
ferniser $alt
fertiliser $alt
@@ -5550,7 +5549,7 @@ halver $alt
harceler $alt
harmoner $alt
harmoniser $alt
harpuner $alt
harpunere $alt
havarer $alt
hektografer $alt
herbariser $alt
@@ -5669,7 +5668,7 @@ intriger $alt
introducer $alt
intuber $alt
invader $alt
invalider $alt
invalidere $alt
inventer $alt
inverter $alt
invester $alt
@@ -5890,7 +5889,6 @@ laminer $alt
lancer $alt
lasere $alt
latiniser $alt
//lavere $alt
lavpasteuriser $alt
legaliser $alt
leger $alt
@@ -6119,7 +6117,7 @@ plakater $alt
planere $alt
plastificer $alt
platiner $alt
pletter $alt
plettere $alt
plisser $alt
plomber $alt
plæder $alt
@@ -6153,7 +6151,7 @@ privileger $alt
prober $alt
problematiser $alt
proceder $alt
producer $alt
producere $alt
profaner $alt
professionaliser $alt
profeter $alt
@@ -6190,7 +6188,7 @@ præferer $alt
præjudicer $alt
prækvalificer $alt
præluder $alt
præmier $alt
præmiere $alt
prænumerer $alt
præparer $alt
præsenter $alt
@@ -6218,7 +6216,7 @@ ramponer $alt
ranger $alt
rappeller $alt
rapportere $alt
raser $alt
rasere $alt
ratificer $alt
ratihaber $alt
rationaliser $alt
@@ -6256,7 +6254,7 @@ reimporter $alt
reinvester $alt
rejicer $alt
rekapituler $alt
reklamer $alt
reklamere $alt
rekognoscer $alt
rekommander $alt
rekompenser $alt
@@ -6418,7 +6416,7 @@ stabiliser $alt
staffer $alt
stagner $alt
standardiser $alt
stationer $alt
stationere $alt
statuere $alt
stenciler $alt
stenografer $alt
@@ -6492,9 +6490,9 @@ temperer $alt
tender $alt
teoretiser $alt
termografer $alt
terrasser $alt
terrassere $alt
terroriser $alt
testamenter $alt
testamentere $alt
testere $alt
tiere $alt
titrer $alt
@@ -6565,7 +6563,7 @@ verbaliser $alt
verificer $alt
verser $alt
versificer $alt
versioner $alt
versionere $alt
vibrer $alt
vidimer $alt
vikarier $alt
@@ -10300,23 +10298,24 @@ også Vs@ // also
idet id'e // in so far as
bleg blaj
blegrød blajrWD
blegrøde blajrWD@
//blege blaj@
blegemiddel bl&#j@mid@l
//blegansigt bl&#jansegt
slags sl'ags // sort, type
tre tr'e // the number 3
barber bab'er // PB barber
barbere bab'eV // PB barbere
barberer bab'eV // PB barberer
//barber bAb'er // PB barber
//barbere bab'eV // PB barbere
//barberer bab'eV // PB barberer
//barberes bab'eVs // PB barberes
barbererne bab'eVn@ // PB barberene
barberenes bab'eVn@s // PB barberenes
//barbererne bab'eVn@ // PB barberene
//barberenes bab'eVn@s // PB barberenes
rejicere rejis'eV // PB should not be pronounced [raje]
rejicerer rejis'eV // PB
rejiceres rejis'eVs // PB
rejicering rejis'eRiN // PB
gele sjel'e // PB gele
géle sjel'e // PB géle
gelé sjel'e // PB gelé
geleen sjel'e@-n // PB geleen
geleer sjel'e3 // PB geleer
geleens sjel'e@-ns // PB geleens
@@ -10361,6 +10360,7 @@ shampu Sjambo // PB Danish pronunciation - oo has been replaced b
(tour de force) tu:@d@||'fV:s // PB
(al qaeda) al||k'ajda // PB
(force majeure) fVrs||,ma'sjW:r // PB
(diner transportable) din'e|trANspVt'abl@ // PB
(quiche lorraine) kiS||lor'E:n:
(fait accompli) fEtakVmpl'i // PB
wien v'i:n // PB Wien - the town of Vienna
@@ -10406,6 +10406,8 @@ dna $abbrev
sos $abbrev // PB the SOS signal
pharm fA:rm? $hasdot // PB fx cand. pharm.
phil fil/3 $hasdot // PB fx cand. phil.
bh $abbrev
(bh'er) b,e:h'O:V
// Try to catch errors
@@ -10439,6 +10441,7 @@ sig si $capital //PB Sig = si with capital S - Sig det med blom
(vi steg) vi||st'e
(de steg) di||st'e
(alle steg) &l3||st'e
steg sdaj $atend $sentence
steget ste@d
// PB problem with noun "hav" = ocean and verb "hav(e)" = to have [hAu]/[h&v]
(et hav) ed||h'Au // PB "et hav" = an ocean - not "hav en god dag" - have a nice day
@@ -10472,6 +10475,7 @@ legenderne leg'EndVn3s
(så længe) sV||l'EN3
(så må) sV||m'O
(så har) sV||har
så sV $sentence $atstart
(virkede så) v'irkeD@||sV
(kom så) kVm||sV
(koste med) kosd@||mED
+618 -157
View File
File diff suppressed because it is too large Load Diff
+1 -1
View File
@@ -62,7 +62,7 @@ W# y Y
* - : ? b B d D
dZ f g h j J k l
l/2 l/3 m n N p r R
s S t T tS v w
s S t T tS v w z
Dictionary hu_dict
+6
View File
@@ -792,6 +792,7 @@ chloroplast $1
chocolate tS0kl@t
cholera k0l@r@
cholesterol k@lEst@r0l
chorizo tSOr'i:zoU
chromosome kroUm@soUm
ciao tSaU
cigar sI2gA@
@@ -1003,6 +1004,7 @@ dose doUs
dosage doUsI2dZ
dramatic dr@matIk
drawer drO@
dreamt drEmpt
drier draI3
driest draI|@st
duet dju:'Et
@@ -1221,6 +1223,7 @@ havoc hav@k
hasty heIstI
hatred heItrI2d
hazardous haz3d@s
headfirst $2
heh hEh
hehe hi:h'i:
heifer hEf@
@@ -1492,6 +1495,7 @@ metaphor mEt@fO@
metallic mEt'alIk
miaou mi:'aU
miaow mi:'aU
mic maIk
mica maIk@
microorganism maIkroU'O@g@nIz@m
midday m,Idd'eI
@@ -1759,6 +1763,7 @@ preset pri:sEt
prestige prEst'i:Z
?3 pretense pri:tEns
pretext pri:tEkst
pretrial pri:tr'aI|@L
pretty prItI
privation praIv'eIS@n
privilege prIvI2lI2dZ
@@ -3096,6 +3101,7 @@ thy ,DaI
thine ,DaIn
me ,mi: $only
me mi: $atstart $atend
him ,hIm $only
us ,Vz $only
us $abbrev $allcaps
+3 -3
View File
@@ -24,7 +24,7 @@
// 2006-11-18 Gilles Casse <gcasse@oralux.org>
//
// Updated 2010-06-11 Michel Such <michel.such@free.fr>
// Updated 2010-06-15 Michel Such <michel.such@free.fr>
//
// * Numbers, a few abbreviations and exceptions.
//
@@ -778,7 +778,7 @@ zut zyt
exocet E2gzosEt
fret fr'Et
budget bydZE2
hamlet hamlEt
hamlet _|amlEt
knesset knesEt
lazaret lazarE2
margaret margarEt
@@ -884,7 +884,7 @@ contentions kO~tA~tjO~z2
dations datjO~z2
désertions dezErtjO~z2 $verb
exploitions EksplwatjO~z2
heurtions hYrtjO~z2
heurtions _|WrtjO~z2
partions partjO~z2
rations ratjO~z2 $verb
tentions tA~tjO~z2
+1460 -1457
View File
File diff suppressed because it is too large Load Diff
+1 -3
View File
@@ -746,9 +746,7 @@
r) u (_A u
u (A_ 'u
ui 'uI
ui (_ uI
ui (s 'uI
ui uI
u (iu w
u (iCK u
uy uI
+3 -3
View File
@@ -393,7 +393,7 @@
_) ட (வல t.V
_) ட (வர t.V
_) ட (ேப t.
_) ட (ாக்ஸி t.
_) டாக (்ஸி t.a:k
.group ண
ண n.V
@@ -597,6 +597,7 @@
_) த (ொம் d
_) த (ோசை d
_) த (ோஷ d
_) த (ுபாய d
//endsort
//sort
@@ -671,6 +672,7 @@ _பார்வ) த (ி t
ச) த (்ரு t
த) த (்ரூப t
பா) த (்ரூம t
_ப) த (ஞ்சலி tV
//endsort
@@ -989,13 +991,11 @@ _முகத்தின்_) ப (ாவ b
சிறு) ப (ிள்ளை p
ஆண்) ப (ிள்ளை p
பெண்) ப (ிள்ளை p
பூம்) ப (ுகார p
ம்) ப (ுரா b
இன்) ப (ுற b
_துன்) ப (ுற b
ப (ுறK p
மண்) ப (ுழு p
பூம்) ப (ுஹார p
ம்) ப (ூர b
ராம்) ப (ூர p
அ) ப (ூர்வ b
Executable
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
+38 -34
View File
@@ -53,7 +53,7 @@ consonants 9 115
id 15 125
sq 33 126
hy 23 117
da 23 119
da 24 120
rw 15 130
ml 13 150
ne 18 156
@@ -82,6 +82,7 @@ b/bu [b] base
b/xb [b] base
[b] fr
[bh] hi
b/xbr [b] fr
d/d [d] base
[d[] base
[d] base2
@@ -139,6 +140,7 @@ d/xd [d] base
[d] sq
d/xd3 [dh] hi
d/xd_pzd [d;] pl
d/xdr [d] fr
d/xdz [dz] consonants
d/x_tap [t#] en
[*] pt
@@ -220,6 +222,7 @@ g/xg [g] base
[g] cy
[g] fr
[g] es
g/xgr [g] fr
h/h_ [h] base
[h] fi
[<h>] la
@@ -338,7 +341,7 @@ l/l_ [l/] base
l/l_@ [l/3] base
[l/] fr
l/l@ [l#] base
[ߵ ] base
[߸ ] base
[l] fr
[l/2] fr
l/L1_aL [l/] base
@@ -364,13 +367,13 @@ l/L2_uL [l/2] base
l/l_3 [l/] de
l/l_4 [ll] sq
l/la [l#] base
[ߵ ] base
[߸ ] base
[l] fr
[l/2] fr
l/l_a [l/3] base
[l/] fr
l/le [l#] base
[ߵ ] base
[߸ ] base
[l] fr
[l/2] fr
l/l_e [l/3] base
@@ -380,7 +383,7 @@ l/L_eL_af [&] af
l/l_front [L] sq
l/l_front_ [l/4] sq
l/li [l#] base
[ߵ ] base
[߸ ] base
[l] fr
[l/2] fr
[l] zh
@@ -392,14 +395,14 @@ ll/_ll [L] bg
l/l_long [l] base
[l] fr
l/lo [l#] base
[ߵ ] base
[߸ ] base
[l] fr
[l/2] fr
l/l_o [l/3] base
[l/] fr
l^/l_rfx [l.] base
l/lu [l#] base
[ߵ ] base
[߸ ] base
[l] fr
[l/2] fr
l/l_u [l/3] base
@@ -617,8 +620,8 @@ ufric/f [f] base
ufric/f_ [f] base
[f] fr
[f] pl
ufric/l# [l#] is
ufric/ll [l#] base
ufric/l# [l#] base
[l#] is
ufric/s [s] base
[s] fr
[z2] fr
@@ -923,6 +926,7 @@ vdiph/ai [aI] base2
[a:I] vi
[aI] id
[aI] hy
[aI] da
vdiph/ai_2 [aI] en
[aI] cy
[aY] cy
@@ -1939,51 +1943,51 @@ vwl_en_us/oor [0] en-us
vwl_en_us/or [o@] en-us
[O:] en-sc
vwl_en_us/ur [U@] en-us
vwl_fr/@2r [ߵ ] fr
vwl_fr/a2r [ߵ ] fr
vwl_fr/aa2r [ߵ ] fr
vwl_fr/@2r [߸ ] fr
vwl_fr/a2r [߸ ] fr
vwl_fr/aa2r [߸ ] fr
vwl_fr/br [r/2] fr
vwl_fr/e2r [ߵ ] fr
vwl_fr/e_2r [ߵ ] fr
vwl_fr/ee2r [ߵ ] fr
vwl_fr/i2r [ߵ ] fr
vwl_fr/e2r [߸ ] fr
vwl_fr/e_2r [߸ ] fr
vwl_fr/ee2r [߸ ] fr
vwl_fr/i2r [߸ ] fr
vwl_fr/j [j/] fr
vwl_fr/o2r [ߵ ] fr
vwl_fr/oo2r [ߵ ] fr
vwl_fr/o2r [߸ ] fr
vwl_fr/oo2r [߸ ] fr
vwl_fr/r [r] fr
[r/2] fr
vwl_fr/r_ [r/] fr
vwl_fr/r_@ [r/] fr
vwl_fr/r@ [ߵ ] fr
vwl_fr/r@ [߸ ] fr
vwl_fr/@R [x] pt-pt
vwl_fr/r@2 [ߵ ] fr
vwl_fr/r@2 [߸ ] fr
vwl_fr/@R2 [R] fr-ca
vwl_fr/ra [ߵ ] fr
vwl_fr/ra [߸ ] fr
vwl_fr/r_a [r/] fr
vwl_fr/raa [ߵ ] fr
vwl_fr/re [ߵ ] fr
vwl_fr/raa [߸ ] fr
vwl_fr/re [߸ ] fr
vwl_fr/r_e [r/] fr
vwl_fr/re2 [ߵ ] fr
vwl_fr/ree [ߵ ] fr
vwl_fr/ri [ߵ ] fr
vwl_fr/re2 [߸ ] fr
vwl_fr/ree [߸ ] fr
vwl_fr/ri [߸ ] fr
vwl_fr/r_i [r/] fr
vwl_fr/rj [ߵ ] fr
vwl_fr/rj [߸ ] fr
vwl_fr/r_n [r/] fr
vwl_fr/ro [ߵ ] fr
vwl_fr/ro [߸ ] fr
vwl_fr/r_o [r/] fr
vwl_fr/roo [ߵ ] fr
vwl_fr/roo [߸ ] fr
vwl_fr/rr [r/] fr
vwl_fr/ru [ߵ ] fr
vwl_fr/ru [߸ ] fr
vwl_fr/r_u [r/] fr
vwl_fr/rw [ߵ ] fr
vwl_fr/ry [ߵ ] fr
vwl_fr/rw [߸ ] fr
vwl_fr/ry [߸ ] fr
vwl_fr/r_y [r/] fr
vwl_fr/tr [r/2] fr
vwl_fr/trr [r/] fr
vwl_fr/u2r [ߵ ] fr
vwl_fr/u2r [߸ ] fr
vwl_fr/wa [w] fr
[w/] fr
vwl_fr/y2r [ߵ ] fr
vwl_fr/y2r [߸ ] fr
vwl_hi/l-voc [l-] base
[l-] sk
[l:] sk
BIN
View File
Binary file not shown.
+11
View File
@@ -0,0 +1,11 @@
ENVELOPE
0 60
5 63
22 92
31 100
41 95
85 12
90 5
100 0
+6
View File
@@ -0,0 +1,6 @@
ENVELOPE
0 0
45 95
100 0
Executable
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
+124
View File
@@ -0,0 +1,124 @@
tune s1
prehead 46 57
headenv fall 16
head 4 80 50 -8 -5
headextend 0 63 38 13 0
nucleus0 fall 64 8
nucleus fall 70 18 24 12
endtune
tune c1
prehead 46 57
headenv fall 16
head 4 80 46 -8 -5
headextend 0 63 38 13 0
nucleus0 fall-rise 80 18
nucleus fall-rise2 78 22 34 52
endtune
tune q1
prehead 46 57
headenv fall 16
head 4 75 43 -7 0
headextend 25 63 38 13 0
nucleus0 fall-rise 88 22
nucleus fall-rise2 82 22 34 66
endtune
tune e1
prehead 46 57
headenv fall 16
head 3 90 50 -9 0
headextend 16 82 50 32 16
nucleus0 fall 92 8
nucleus fall 92 80 76 8
endtune
// PB Tunes for the Danish intonation
// full-stop "." - punktum
tune s2
prehead 46 57
headenv fall 16
head 4 65 60 -8 -5
headextend 0 53 38 13 0
nucleus0 fall 44 28
nucleus fall 50 42 34 28 // sidste ord før punktu
onset 75 -5 -5
endtune
// comma "," - komma
tune c2
prehead 46 57
headenv fall 16
head 4 65 50 -8 -5
headextend 0 63 38 13 0
nucleus0 rise 60 42
nucleus rise 55 42 34 52 // sidste tal: slutniveau
endtune
// question mark "?" - spørgsmålste
tune q2
prehead 40 75
headenv fall 16
head 4 75 43 -7 0 //head 4 35 43 -7 0
headextend 25 63 38 13 0
nucleus0 rise 70 50 // første tal: slutniveaue
nucleus rise 35 45 60 70 // sidste tal: slutniveau
endtune
// exclamation mark "!" - udråbsteg
tune e2
prehead 46 57
headenv fall 16
head 3 90 50 -9 0
headextend 16 82 50 32 16
nucleus0 fall 92 8
nucleus fall 92 80 76 8
endtune
// Tunes for the French intonation
// full-stop "." - point
tune s3
prehead 46 57
headenv fall 16
head 4 80 50 -8 -5
headextend 0 63 38 13 0
nucleus0 fall 64 8
nucleus fall 70 18 24 12
endtune
// comma "," - virgule
tune c3
prehead 46 57
headenv fall 16
head 4 80 30 -5 -15
headextend 25 63 38 13 0
nucleus0 fall-rise 75 40
endtune
// question mark "?" - point d'interrogation
tune q3
prehead 46 57
headenv fall 16
head 4 75 43 -7 0
headextend 25 63 38 13 0
nucleus0 fall-rise 88 22
nucleus fall-rise2 82 22 34 66
endtune
// exclamation mark "!" - point d'exclamation
tune e3
prehead 46 57
headenv fall 16
head 3 90 50 -9 0
headextend 16 82 50 32 16
nucleus0 fall 92 8
nucleus fall 92 80 76 8
endtune
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
Binary file not shown.
+7
View File
@@ -114,6 +114,13 @@ phoneme W#
FMT(vowel/V)
endphoneme
phoneme aI
vowel starttype #a endtype #i
length 250
FMT(vdiph/ai)
endphoneme
// CONSONANTS
// PB added l/3
+2 -2
View File
@@ -383,7 +383,7 @@ endphoneme
phoneme aI@
vowel starttype #a endtype #@
length 270
length 280
IfNextVowelAppend(r-)
FMT(vwl_en/aI@)
endphoneme
@@ -391,7 +391,7 @@ endphoneme
phoneme aU@
vowel starttype #a endtype #@
length 270
length 280
IfNextVowelAppend(r-)
FMT(vwl_en/aU@)
endphoneme
+2 -2
View File
@@ -239,7 +239,7 @@ endphoneme
phoneme aI@
vowel starttype #a endtype #@
length 270
length 280
IfNextVowelAppend(r-)
FMT(vwl_en/aI@)
endphoneme
@@ -247,7 +247,7 @@ endphoneme
phoneme aU@
vowel starttype #a endtype #@
length 270
length 280
IfNextVowelAppend(r-)
FMT(vwl_en/aU@)
endphoneme
+2 -2
View File
@@ -222,7 +222,7 @@ endphoneme
phoneme aI@
vowel starttype #a endtype #@
length 270
length 280
IfNextVowelAppend(r-)
FMT(vwl_en/ooi@)
endphoneme
@@ -230,7 +230,7 @@ endphoneme
phoneme aU@
vowel starttype #a endtype #@
length 270
length 280
IfNextVowelAppend(r-)
FMT(vwl_en/aU@)
endphoneme
+19 -8
View File
@@ -1,7 +1,7 @@
//====================================================
// French
//====================================================
// Updated 2010-06-12 Michel Such <michel.such@free.fr>
// Updated 2010-06-16 Michel Such <michel.such@free.fr>
phoneme #l virtual
// Used for l and l/
@@ -80,8 +80,7 @@ phoneme r
vcd uvl frc nopause
rhotic
starttype #r endtype #r
Vowelin f1=1 f2=1600 -500 500 f3=-200 100 len=65
Vowelout f1=1 f2=1200 -400 800 f3=200 100 len=60
Vowelin f1=0 f2=1500 -400 400 f3=-400 80
lengthmod 7
IF nextPh(isNotVowel) THEN
@@ -148,7 +147,7 @@ endphoneme
phoneme r/2
liquid rhotic uvl nopause
starttype #r endtype #r
Vowelin f1=1 f2=1600 -500 500 f3=-200 100 len=65 amp=8
Vowelin f1=0 f2=1500 -400 400 f3=-400 80
CALL post_r
IF prevPhW(f) OR prevPhW(k) OR prevPhW(p) OR prevPhW(s) OR prevPhW(t) OR prevPhW(S) THEN
@@ -163,7 +162,7 @@ endphoneme
phoneme l
liquid nopause
liquid
starttype #l endtype #l
lengthmod 7
@@ -639,7 +638,11 @@ phoneme b
ENDIF
IF PreVoicing THEN
FMT(b/xb)
IF nextPhW(#r) THEN
FMT(b/xbr)
ELSE
FMT(b/xb)
ENDIF
ENDIF
IF nextPh(isPause2) OR nextPh(l) THEN
@@ -663,7 +666,11 @@ phoneme d
Vowelout f1=2 f2=1700 -300 300 f3=-100 80
IF PreVoicing THEN
FMT(d/xd)
IF nextPhW(#r) THEN
FMT(d/xdr)
ELSE
FMT(d/xd)
ENDIF
ENDIF
IF nextPh(isPause2) THEN
@@ -699,7 +706,11 @@ phoneme g
Vowelout f1=1 f2=2300 250 300 f3=-300 80 brk
IF PreVoicing THEN
FMT(g/xg)
IF nextPhW(#r) THEN
FMT(g/xgr)
ELSE
FMT(g/xg)
ENDIF
ENDIF
IF nextPh(isPause2) THEN
+16
View File
@@ -0,0 +1,16 @@
//====================================================
// Nahuatl (classical)
//====================================================
phoneme : // lengthens the previous vowel by 'length'
virtual
length 300
endphoneme
phoneme e
vowel starttype #e endtype #e
length 170
FMT(vowel/e_mid2)
endphoneme
+4 -1
View File
@@ -80,7 +80,10 @@ endphoneme
phoneme u
vowel starttype #u endtype #u
length 110
ChangeIfNotStressed(U)
IF prevPhW(isVel) THEN
ELSE
ChangeIfNotStressed(U)
ENDIF
FMT(vowel/u_6)
endphoneme
+7 -2
View File
@@ -1487,7 +1487,7 @@ phoneme l# // Lateral fricative (eg. Welsh "ll")
VowelEnding(l/xl, -40)
ENDIF
WAV(ufric/ll, 60)
WAV(ufric/l#, 60)
endphoneme
@@ -1720,6 +1720,12 @@ phonemetable da base
include ph_danish
// The following lines are experimental, for future additions.
// These langauges are not in a usable state.
// These lines can be deleted.
phonemetable rw base2
include ph_kinyarwanda
@@ -1738,7 +1744,6 @@ include ph_nepali
//phonemetable mr hi
//include ph_marathi
//phonemetable eu base2
//include ph_basque
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
+2 -2
View File
@@ -49,12 +49,12 @@ endif
speak_SOURCES = speak.cpp compiledict.cpp dictionary.cpp intonation.cpp \
readclause.cpp setlengths.cpp numbers.cpp synth_mbrola.cpp \
synthdata.cpp synthesize.cpp translate.cpp \
synthdata.cpp synthesize.cpp translate.cpp mbrowrap.cpp \
tr_languages.cpp voices.cpp wavegen.cpp phonemelist.cpp klatt.cpp
libespeak_SOURCES = speak_lib.cpp compiledict.cpp dictionary.cpp intonation.cpp \
readclause.cpp setlengths.cpp numbers.cpp synth_mbrola.cpp \
synthdata.cpp synthesize.cpp translate.cpp \
synthdata.cpp synthesize.cpp translate.cpp mbrowrap.cpp \
tr_languages.cpp voices.cpp wavegen.cpp phonemelist.cpp \
espeak_command.cpp event.cpp fifo.cpp $(WAVE) debug.cpp klatt.cpp
+17 -10
View File
@@ -1,20 +1,27 @@
SRCS=\
compiledata.cpp compiledict.cpp debug.cpp dictionary.cpp espeak_command.cpp espeakedit.cpp \
event.cpp extras.cpp fifo.cpp formantdlg.cpp intonation.cpp klatt.cpp menus.cpp numbers.cpp \
options.cpp phonemelist.cpp prosodydisplay.cpp readclause.cpp setlengths.cpp speak_lib.cpp \
spect.cpp spectdisplay.cpp spectseq.cpp synthdata.cpp synthesize.cpp synth_mbrola.cpp \
translate.cpp transldlg.cpp tr_languages.cpp voicedlg.cpp voices.cpp vowelchart.cpp wave.cpp \
wavegen.cpp
# Makefile for 'espeakedit' program
SRCS= compiledata.cpp compiledict.cpp debug.cpp dictionary.cpp espeak_command.cpp \
espeakedit.cpp event.cpp extras.cpp fifo.cpp formantdlg.cpp intonation.cpp \
klatt.cpp mbrowrap.cpp menus.cpp numbers.cpp options.cpp phonemelist.cpp \
prosodydisplay.cpp readclause.cpp setlengths.cpp speak_lib.cpp spect.cpp \
spectdisplay.cpp spectseq.cpp synthdata.cpp synthesize.cpp synth_mbrola.cpp \
translate.cpp transldlg.cpp tr_languages.cpp voicedlg.cpp voices.cpp vowelchart.cpp \
wave.cpp wavegen.cpp
OBJS=$(patsubst %.cpp,%.o,$(SRCS))
WX_LIBS = -pthread -lwx_gtk2u_xrc-2.6 -lwx_gtk2u_qa-2.6 -lwx_gtk2u_html-2.6 -lwx_gtk2u_adv-2.6 -lwx_gtk2u_core-2.6 -lwx_baseu_xml-2.6 -lwx_baseu_net-2.6 -lwx_baseu-2.6
WX_LIBS = -pthread -lwx_gtk2u_xrc-2.6 -lwx_gtk2u_qa-2.6 -lwx_gtk2u_html-2.6 \
-lwx_gtk2u_adv-2.6 -lwx_gtk2u_core-2.6 -lwx_baseu_xml-2.6 -lwx_baseu_net-2.6 -lwx_baseu-2.6
LIBS=-lstdc++ -lportaudio
CPPFLAGS = -Wall -g -fexceptions -I/usr/lib/wx/include/gtk2-unicode-release-2.6 -I/usr/include/wx-2.6 -DGTK_NO_CHECK_CASTS -D__WXGTK__ -D_FILE_OFFSET_BITS=64 -D_LARGE_FILES -D_LARGEFILE_SOURCE=1 -DNO_GCC_PRAGMA -D_ESPEAKEDIT
CPPFLAGS = -Wall -g -fexceptions -I/usr/lib/wx/include/gtk2-unicode-release-2.6
-I/usr/include/wx-2.6 \
-DGTK_NO_CHECK_CASTS -D__WXGTK__ -D_FILE_OFFSET_BITS=64 -D_LARGE_FILES
-D_LARGEFILE_SOURCE=1 -DNO_GCC_PRAGMA -D_ESPEAKEDIT
CXXFLAGS = -O2 -g0 -Wall -g -fexceptions -I/usr/lib/wx/include/gtk2-unicode-release-2.6 -I/usr/include/wx-2.6 -DGTK_NO_CHECK_CASTS -D__WXGTK__ -D_FILE_OFFSET_BITS=64 -D_LARGE_FILES -D_LARGEFILE_SOURCE=1 -DNO_GCC_PRAGMA -D_ESPEAKEDIT
CXXFLAGS = -O2 -g0 -Wall -g -fexceptions -I/usr/lib/wx/include/gtk2-unicode-release-2.6 -I/usr/include/wx-2.6 \
-DGTK_NO_CHECK_CASTS -D__WXGTK__ -D_FILE_OFFSET_BITS=64 -D_LARGE_FILES -D_LARGEFILE_SOURCE=1 -DNO_GCC_PRAGMA -D_ESPEAKEDIT
all: espeakedit
+4 -4
View File
@@ -1744,12 +1744,12 @@ static int LoadWavefile(FILE *f, const char *fname)
sr2 = Read4Bytes(f);
fseek(f,40,SEEK_SET);
if((sr1 != samplerate) || (sr2 != sr1*2))
if((sr1 != samplerate_native) || (sr2 != sr1*2))
{
#ifdef PLATFORM_WINDOWS
if(sr1 != samplerate)
if(sr1 != samplerate_native)
{
fprintf(f_errors,"Wrong samplerate %d, wants %d\n",sr1,samplerate);
fprintf(f_errors,"Wrong samplerate %d, wants %d\n",sr1,samplerate_native);
error("Wrong samplerate: %s",fname);
}
if(sr2 != sr1*2)
@@ -1764,7 +1764,7 @@ static int LoadWavefile(FILE *f, const char *fname)
if((fd_temp = mkstemp(fname_temp)) >= 0)
{
close(fd_temp);
sprintf(command,"sox \"%s%s.wav\" -r %d -c 1 -w %s polyphase\n",path_source,fname,samplerate,fname_temp);
sprintf(command,"sox \"%s%s.wav\" -r %d -c 1 -w %s polyphase\n",path_source,fname,samplerate_native,fname_temp);
if(system(command) < 0)
{
error("Failed to resample: %s",command);
+49 -28
View File
@@ -66,8 +66,10 @@ static const char *help_text =
"\t directory. <voice name> specifies the language\n"
"--path=\"<path>\"\n"
"\t Specifies the directory containing the espeak-data directory\n"
"--pho\n"
"\t Write mbrola phoneme data (.pho) to stdout, or to the file in --phonout\n"
"--phonout=\"<filename>\"\n"
"\t Write output from -x -X commands, and mbrola phoneme data, to this file\n"
"\t Write phoneme output from -x -X and --pho to this file\n"
"--punct=\"<characters>\"\n"
"\t Speak the names of punctuation characters during speaking. If\n"
"\t =<characters> is omitted, all punctuation is spoken.\n"
@@ -87,6 +89,7 @@ int samplerate;
int quiet = 0;
unsigned int samples_total = 0;
unsigned int samples_split = 0;
unsigned int samples_split_seconds = 0;
unsigned int wavefile_count = 0;
FILE *f_wavfile = NULL;
@@ -218,15 +221,18 @@ int OpenWavFile(char *path, int rate)
else
f_wavfile = fopen(path,"wb");
if(f_wavfile != NULL)
if(f_wavfile == NULL)
{
fwrite(wave_hdr,1,24,f_wavfile);
Write4Bytes(f_wavfile,rate);
Write4Bytes(f_wavfile,rate * 2);
fwrite(&wave_hdr[32],1,12,f_wavfile);
return(0);
fprintf(stderr,"Can't write to: '%s'\n",path);
return(1);
}
return(1);
fwrite(wave_hdr,1,24,f_wavfile);
Write4Bytes(f_wavfile,rate);
Write4Bytes(f_wavfile,rate * 2);
fwrite(&wave_hdr[32],1,12,f_wavfile);
return(0);
} // end of OpenWavFile
@@ -266,25 +272,40 @@ static int SynthCallback(short *wav, int numsamples, espeak_EVENT *events)
return(0);
}
if(samples_split > 0)
while(events->type != 0)
{
// start a new WAV file when this limit is reached, at the next sentence boundary
while(events->type != 0)
if(events->type == espeakEVENT_SAMPLERATE)
{
if((events->type == espeakEVENT_SENTENCE) && (samples_total > samples_split))
samplerate = events->id.number;
samples_split = samples_split_seconds * samplerate;
}
else
if(events->type == espeakEVENT_SENTENCE)
{
// start a new WAV file when the limit is reached, at this sentence boundary
if((samples_split > 0) && (samples_total > samples_split))
{
CloseWavFile();
samples_total = 0;
wavefile_count++;
}
events++;
}
events++;
}
if(f_wavfile == NULL)
{
sprintf(fname,"%s_%.2d%s",wavefile,++wavefile_count,filetype);
if(OpenWavFile(fname, samplerate) != 0)
return(1);
if(samples_split > 0)
{
sprintf(fname,"%s_%.2d%s",wavefile,wavefile_count+1,filetype);
if(OpenWavFile(fname, samplerate) != 0)
return(1);
}
else
{
if(OpenWavFile(wavefile, samplerate) != 0)
return(1);
}
}
if(numsamples > 0)
@@ -332,7 +353,8 @@ int main (int argc, char **argv)
{"stdout", no_argument, 0, 0x105},
{"split", optional_argument, 0, 0x106},
{"path", required_argument, 0, 0x107},
{"phonout", required_argument, 0, 0x108},
{"phonout", required_argument, 0, 0x108},
{"pho", no_argument, 0, 0x109},
{0, 0, 0, 0}
};
@@ -360,7 +382,8 @@ int main (int argc, char **argv)
int wordgap = -1;
int option_capitals = -1;
int option_punctuation = -1;
int option_phonemes = -1;
int option_phonemes = 0;
int option_mbrola_phonemes = 0;
int option_linelength = 0;
int option_waveout = 0;
@@ -550,9 +573,9 @@ int main (int argc, char **argv)
case 0x106: // -- split
if(optarg2 == NULL)
samples_split = 30; // default 30 minutes
samples_split = 30 * 60; // default 30 minutes
else
samples_split = atoi(optarg2);
samples_split = atoi(optarg2) * 60;
break;
case 0x107: // --path
@@ -566,6 +589,10 @@ int main (int argc, char **argv)
}
break;
case 0x109: // --pho
option_mbrola_phonemes = 8;
break;
default:
exit(0);
}
@@ -576,7 +603,7 @@ int main (int argc, char **argv)
{
// writing to a file (or no output), we can use synchronous mode
samplerate = espeak_Initialize(AUDIO_OUTPUT_SYNCHRONOUS,0,data_path,0);
samples_split = (samplerate * samples_split) * 60;
samples_split = samplerate * samples_split_seconds;
espeak_SetSynthCallback(SynthCallback);
if(samples_split)
@@ -589,12 +616,6 @@ int main (int argc, char **argv)
*extn = 0;
}
}
else
if(option_waveout)
{
if(OpenWavFile(wavefile,samplerate) != 0)
exit(4);
}
}
else
{
@@ -641,7 +662,7 @@ int main (int argc, char **argv)
espeak_SetParameter(espeakLINELENGTH,option_linelength,0);
if(option_punctuation == 2)
espeak_SetPunctuationList(option_punctlist);
espeak_SetPhonemeTrace(option_phonemes,f_phonemes_out);
espeak_SetPhonemeTrace(option_phonemes | option_mbrola_phonemes,f_phonemes_out);
if(filename[0]==0)
{
-2
View File
@@ -129,8 +129,6 @@ char param[80];
if(argc > 1)
{
extern void VoiceReset(int control);
p = argv[1];
j = 0;
while((param[j] = p[j]) != 0) j++;
-205
View File
@@ -1,205 +0,0 @@
#ifndef MBROLIB_H
#define MBROLIB_H
/*
* mbrolib: mbrola wrapper.
*
* Copyright (C) 2007 Gilles Casse <gcasse@oralux.org>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 3 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*
*/
#ifdef __cplusplus
extern "C" {
#endif
/* < types */
/** Parameters */
typedef struct {
int ignore_error; /* 1=Ignore any fatal error or unknown diphone */
char comment_char; /* Comment character */
float volume_ratio; /* Volume ratio */
float frequency_ratio; /* Applied to pitch points */
float time_ratio; /* Applied to phone durations */
} mbrolib_parameter;
/** Returned errors */
typedef enum {
MBROLIB_OK=0,
MBROLIB_DATABASE_NOT_INSTALLED,
MBROLIB_INVAL,
MBROLIB_OUT_OF_MEMORY,
MBROLIB_OUT_OF_RANGE,
MBROLIB_READ_ERROR,
MBROLIB_WRITE_ERROR
} MBROLIB_ERROR;
/** Gender */
typedef enum {
MBROLIB_FEMALE,
MBROLIB_MALE
} MBROLIB_GENDER;
/** Voice descriptor */
typedef struct {
char *name; /* name (for example: "en1") */
char *filename; /* database pathname (for example: "/usr/share/mbrola/voices/en1) */
int rate; /* database sample rate */
MBROLIB_GENDER gender;
const char *language; /* Language and optional dialect qualifier in ascii (e.g. en, fr_ca). */
} mbrolib_voice;
/* > */
/** Initialization, returns a new handle.
First function.
@param the_sample_rate: output rate in Hz (for example 22050). If 0, keep the original database rate.
@return handle (or NULL if error).
*/
void* mbrolib_init( int sample_rate);
typedef void* (t_mbrolib_init)(int);
/** Returns the list of the installed mbrola databases.
The databases are searched according to the MBROLA_PATH environment variable if set,
or under a default path otherwise (see MBROLA_PATH in mbrolib.c).
An array of voices is returned. The last item is set to NULL.
The caller must not free the returned items or the array.
@param the_handle previously given by mbrolib_init.
@return An array of voices.
*/
const mbrolib_voice ** mbrolib_list_voices( void* the_handle);
typedef const mbrolib_voice ** (t_mbrolib_list_voices)(void*);
/** Set voice
@param the_handle.
@param the_database (for example, "en1").
@return error code (MBROLIB_OK, MBROLIB_DATABASE_NOT_INSTALLED, MBROLIB_INVAL).
*/
MBROLIB_ERROR mbrolib_set_voice( void* the_handle, const char* the_name);
typedef MBROLIB_ERROR (t_mbrolib_set_voice)( void*, const char*);
/** Get the current database parameters.
The caller supplies a pointer to an already allocated structure.
@param the_handle previously given by mbrolib_init.
@param the_parameters: pointer to the structure.
@return error code (MBROLIB_OK, MBROLIB_INVAL).
*/
MBROLIB_ERROR mbrolib_get_parameter(void* the_handle, mbrolib_parameter* the_parameter);
typedef MBROLIB_ERROR (t_mbrolib_get_parameter)(void*, mbrolib_parameter*);
/** Set the database parameters using the supplied data.
@param the_handle previously given by mbrolib_init.
@param the_parameters: pointer to the wished parameters.
@return error code (MBROLIB_OK, MBROLIB_INVAL).
*/
MBROLIB_ERROR mbrolib_set_parameter(void* the_handle, const mbrolib_parameter* the_parameter);
typedef MBROLIB_ERROR (t_mbrolib_set_parameter)(void*, const mbrolib_parameter*);
/** Write the mbrola phonemes in the internal buffer.
@param the_handle.
@param the_mbrola_phonemes.
@param the_size in bytes.
@return error code (MBROLIB_OK, MBROLIB_INVAL, MBROLIB_WRITE_ERROR, MBROLIB_READ_ERROR).
*/
MBROLIB_ERROR mbrolib_write(void* the_handle, const char* the_mbrola_phonemes, size_t the_size);
typedef MBROLIB_ERROR (t_mbrolib_write)(void*, const char*, size_t);
/** Read n bytes of the output samples.
@param the_handle.
@param the_samples (raw audio data, 16bits, mono).
@param the_size max number of int16 to read.
@param the_size number of int16 read.
@return error code (MBROLIB_OK, MBROLIB_INVAL, MBROLIB_READ_ERROR).
*/
MBROLIB_ERROR mbrolib_read(void* the_handle, short* the_samples, int the_max_size, int* the_read_size);
typedef MBROLIB_ERROR (t_mbrolib_read)(void*, short*, int, int*);
/** Flush
@param the_handle.
*/
void mbrolib_flush(void* the_handle);
typedef void (t_mbrolib_flush)(void*);
/** Release the handle
@param the_handle.
@return error code (MBROLIB_OK, MBROLIB_INVAL).
*/
MBROLIB_ERROR mbrolib_terminate(void* the_handle);
typedef MBROLIB_ERROR (t_mbrolib_terminate)(void*);
#ifdef __cplusplus
}
#endif
#endif
+578
View File
@@ -0,0 +1,578 @@
/*
* mbrowrap -- A wrapper library around the mbrola binary
* providing a subset of the API from the Windows mbrola DLL.
*
* Copyright (C) 2010 by Nicolas Pitre <nico@fluxnic.net>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#include <stdarg.h>
#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <malloc.h>
#include <signal.h>
#include <fcntl.h>
#include <poll.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/wait.h>
#include "mbrowrap.h"
/*
* mbrola instance parameters
*/
enum mbr_state {
MBR_INACTIVE = 0,
MBR_IDLE,
MBR_NEWDATA,
MBR_AUDIO,
MBR_WEDGED
};
static enum mbr_state mbr_state;
static char *mbr_voice_path;
static int mbr_cmd_fd, mbr_audio_fd, mbr_error_fd, mbr_proc_stat;
static pid_t mbr_pid;
static int mbr_samplerate;
static float mbr_volume = 1.0;
static char mbr_errorbuf[160];
struct datablock {
struct datablock *next;
int done;
int size;
char buffer[1]; /* 1 or more, dynamically allocated */
};
static struct datablock *mbr_pending_data_head, *mbr_pending_data_tail;
/*
* Private support code.
*/
static void log(const char *msg, ...)
{
va_list params;
va_start(params, msg);
vfprintf(stderr, msg, params);
fputc('\n', stderr);
va_end(params);
}
static void err(const char *err, ...)
{
va_list params;
va_start(params, err);
vsnprintf(mbr_errorbuf, sizeof(mbr_errorbuf), err, params);
va_end(params);
log("mbrola error: \"%s\"", mbr_errorbuf);
}
static int create_pipes(int p1[2], int p2[2], int p3[2])
{
int error=0;
if (pipe(p1) != -1) {
if (pipe(p2) != -1) {
if (pipe(p3) != -1) {
return 0;
} else
error = errno;
close(p2[0]);
close(p2[1]);
} else
error = errno;
close(p1[0]);
close(p1[1]);
}
err("pipe(): %s", strerror(error));
return -1;
}
static void close_pipes(int p1[2], int p2[2], int p3[2])
{
close(p1[0]);
close(p1[1]);
close(p2[0]);
close(p2[1]);
close(p3[0]);
close(p3[1]);
}
static int start_mbrola(const char *voice_path)
{
int error, p_stdin[2], p_stdout[2], p_stderr[2];
char charbuf[20];
if (mbr_state != MBR_INACTIVE) {
err("mbrola init request when already initialized");
return -1;
}
error = create_pipes(p_stdin, p_stdout, p_stderr);
if (error)
return -1;
mbr_pid = fork();
if (mbr_pid == -1) {
error = errno;
close_pipes(p_stdin, p_stdout, p_stderr);
err("fork(): %s", strerror(error));
return -1;
}
if (mbr_pid == 0) {
int i;
if (dup2(p_stdin[0], 0) == -1 ||
dup2(p_stdout[1], 1) == -1 ||
dup2(p_stderr[1], 2) == -1) {
snprintf(mbr_errorbuf, sizeof(mbr_errorbuf),
"dup2(): %s\n", strerror(errno));
write(p_stderr[1], mbr_errorbuf, strlen(mbr_errorbuf));
_exit(1);
}
for (i = p_stderr[1]; i > 2; i--)
close(i);
signal(SIGHUP, SIG_IGN);
signal(SIGINT, SIG_IGN);
signal(SIGQUIT, SIG_IGN);
signal(SIGTERM, SIG_IGN);
snprintf(charbuf, sizeof(charbuf), "%g", mbr_volume);
execlp("mbrola", "mbrola", "-e", "-v", charbuf,
voice_path, "-", "-.wav", (char *)NULL);
/* if execution reaches this point then the exec() failed */
snprintf(mbr_errorbuf, sizeof(mbr_errorbuf),
"mbrola: %s\n", strerror(errno));
write(2, mbr_errorbuf, strlen(mbr_errorbuf));
_exit(1);
}
snprintf(charbuf, sizeof(charbuf), "/proc/%d/stat", mbr_pid);
mbr_proc_stat = open(charbuf, O_RDONLY);
if (mbr_proc_stat == -1) {
error = errno;
close_pipes(p_stdin, p_stdout, p_stderr);
waitpid(mbr_pid, NULL, 0);
mbr_pid = 0;
err("/proc is unaccessible: %s", strerror(error));
return -1;
}
signal(SIGPIPE, SIG_IGN);
if (fcntl(p_stdin[1], F_SETFL, O_NONBLOCK) == -1 ||
fcntl(p_stdout[0], F_SETFL, O_NONBLOCK) == -1 ||
fcntl(p_stderr[0], F_SETFL, O_NONBLOCK) == -1) {
error = errno;
close_pipes(p_stdin, p_stdout, p_stderr);
waitpid(mbr_pid, NULL, 0);
mbr_pid = 0;
err("fcntl(): %s", strerror(error));
return -1;
}
mbr_cmd_fd = p_stdin[1];
mbr_audio_fd = p_stdout[0];
mbr_error_fd = p_stderr[0];
close(p_stdin[0]);
close(p_stdout[1]);
close(p_stderr[1]);
mbr_state = MBR_IDLE;
return 0;
}
static void stop_mbrola(void)
{
if (mbr_state == MBR_INACTIVE)
return;
close(mbr_proc_stat);
close(mbr_cmd_fd);
close(mbr_audio_fd);
close(mbr_error_fd);
if (mbr_pid) {
kill(mbr_pid, SIGTERM);
waitpid(mbr_pid, NULL, 0);
mbr_pid = 0;
}
mbr_state = MBR_INACTIVE;
}
static void free_pending_data(void)
{
struct datablock *p, *head = mbr_pending_data_head;
while (head) {
p = head;
head = head->next;
free(p);
}
mbr_pending_data_head = NULL;
mbr_pending_data_tail = NULL;
}
static int mbrola_has_errors(void)
{
int result, error;
result = read(mbr_error_fd, mbr_errorbuf, sizeof(mbr_errorbuf)-1);
if (result == -1) {
if (errno == EAGAIN)
return 0;
err("read(error): %s", strerror(errno));
return -1;
}
if (result != 0) {
mbr_errorbuf[result] = 0;
if (mbr_errorbuf[result - 1] == '\n')
mbr_errorbuf[result - 1] = 0;
/* inhibit the reset signal message */
if (strncmp(mbr_errorbuf, "Got a reset signal", 18) == 0) {
mbr_errorbuf[0] = 0;
return 0;
}
/* don't consider this fatal at this point */
error = 0;
} else {
/* EOF on stderr, assume mbrola died. */
pid_t pid;
int status, len;
const char *msg;
char msgbuf[80];
pid = waitpid(mbr_pid, &status, WNOHANG);
if (!pid) {
msg = "mbrola closed stderr and did not exit";
} else {
mbr_pid = 0;
if (WIFSIGNALED(status)) {
int sig = WTERMSIG(status);
snprintf(msgbuf, sizeof(msgbuf),
"mbrola died by signal %d", sig);
msg = msgbuf;
} else if (WIFEXITED(status)) {
int exst = WEXITSTATUS(status);
snprintf(msgbuf, sizeof(msgbuf),
"mbrola exited with status %d", exst);
msg = msgbuf;
} else {
msg = "mbrola died and wait status is weird";
}
}
len = strlen(mbr_errorbuf);
if (!len)
snprintf(mbr_errorbuf, sizeof(mbr_errorbuf), "%s", msg);
else
snprintf(mbr_errorbuf+len, sizeof(mbr_errorbuf)-len,
", (%s)", msg);
error = -1;
}
log("mbrola error: \"%s\"", mbr_errorbuf);
return error;
}
static int send_to_mbrola(const char *cmd)
{
ssize_t result;
int len;
if (!mbr_pid)
return -1;
len = strlen(cmd);
result = write(mbr_cmd_fd, cmd, len);
if (result == -1) {
int error = errno;
if (error == EPIPE && mbrola_has_errors()) {
return -1;
} else if (error == EAGAIN) {
result = 0;
} else {
err("write(): %s", strerror(error));
return -1;
}
}
if (result != len) {
struct datablock *data;
data = (struct datablock *)malloc(sizeof(*data) + len - result);
if (data) {
data->next = NULL;
data->done = 0;
data->size = len - result;
memcpy(data->buffer, cmd + result, len - result);
result = len;
if (!mbr_pending_data_head)
mbr_pending_data_head = data;
else
mbr_pending_data_tail->next = data;
mbr_pending_data_tail = data;
}
}
return result;
}
static int mbrola_is_idle(void)
{
char *p;
char buffer[20]; /* looking for "12345 (mbrola) S" so 20 is plenty*/
/* look in /proc to determine if mbrola is still running or sleeping */
if (lseek(mbr_proc_stat, 0, SEEK_SET) != 0)
return 0;
if (read(mbr_proc_stat, buffer, sizeof(buffer)) != sizeof(buffer))
return 0;
p = (char *)memchr(buffer, ')', sizeof(buffer));
if (!p || (unsigned)(p - buffer) >= sizeof(buffer) - 2)
return 0;
return (p[1] == ' ' && p[2] == 'S');
}
static ssize_t receive_from_mbrola(void *buffer, size_t bufsize)
{
int result, wait = 1;
size_t cursize = 0;
if (!mbr_pid)
return -1;
do {
struct pollfd pollfd[3];
nfds_t nfds = 0;
int idle;
pollfd[0].fd = mbr_audio_fd;
pollfd[0].events = POLLIN;
nfds++;
pollfd[1].fd = mbr_error_fd;
pollfd[1].events = POLLIN;
nfds++;
if (mbr_pending_data_head) {
pollfd[2].fd = mbr_cmd_fd;
pollfd[2].events = POLLOUT;
nfds++;
}
idle = mbrola_is_idle();
result = poll(pollfd, nfds, idle ? 0 : wait);
if (result == -1) {
err("poll(): %s", strerror(errno));
return -1;
}
if (result == 0) {
if (idle) {
mbr_state = MBR_IDLE;
break;
} else {
if (wait >= 5000 * (4-1)/4) {
mbr_state = MBR_WEDGED;
err("mbrola process is stalled");
break;
} else {
wait *= 4;
continue;
}
}
}
wait = 1;
if (pollfd[1].revents && mbrola_has_errors())
return -1;
if (mbr_pending_data_head && pollfd[2].revents) {
struct datablock *head = mbr_pending_data_head;
char *data = head->buffer + head->done;
int left = head->size - head->done;
result = write(mbr_cmd_fd, data, left);
if (result == -1) {
int error = errno;
if (error == EPIPE && mbrola_has_errors())
return -1;
err("write(): %s", strerror(error));
return -1;
}
if (result != left) {
head->done += result;
} else {
mbr_pending_data_head = head->next;
free(head);
if (!mbr_pending_data_head)
mbr_pending_data_tail = NULL;
else
continue;
}
}
if (pollfd[0].revents) {
char *curpos = (char *)buffer + cursize;
size_t space = bufsize - cursize;
ssize_t obtained = read(mbr_audio_fd, curpos, space);
if (obtained == -1) {
err("read(): %s", strerror(errno));
return -1;
}
cursize += obtained;
mbr_state = MBR_AUDIO;
}
} while (cursize < bufsize);
return cursize;
}
/*
* API functions.
*/
int init_MBR(const char *voice_path)
{
int error, result;
unsigned char wavhdr[45];
error = start_mbrola(voice_path);
if (error)
return -1;
result = send_to_mbrola("#\n");
if (result != 2) {
stop_mbrola();
return -1;
}
/* we should actually be getting only 44 bytes */
result = receive_from_mbrola(wavhdr, 45);
if (result != 44) {
err("unable to get .wav header from mbrola");
stop_mbrola();
return -1;
}
/* parse wavhdr to get mbrola voice samplerate */
if (memcmp(wavhdr, "RIFF", 4) != 0 ||
memcmp(wavhdr+8, "WAVEfmt ", 8) != 0) {
err("mbrola did not return a .wav header");
stop_mbrola();
return -1;
}
mbr_samplerate = wavhdr[24] + (wavhdr[25]<<8) +
(wavhdr[26]<<16) + (wavhdr[27]<<24);
//log("mbrola: voice samplerate = %d", mbr_samplerate);
/* remember the voice path for setVolumeRatio_MBR() */
if (mbr_voice_path != voice_path) {
free(mbr_voice_path);
mbr_voice_path = strdup(voice_path);
}
return 0;
}
void close_MBR(void)
{
stop_mbrola();
free_pending_data();
free(mbr_voice_path);
mbr_voice_path = NULL;
mbr_volume = 1.0;
}
int reset_MBR()
{
int result, success = 1;
char dummybuf[4096];
if (mbr_state == MBR_IDLE)
return 1;
if (!mbr_pid)
return 0;
if (kill(mbr_pid, SIGUSR1) == -1)
success = 0;
free_pending_data();
result = write(mbr_cmd_fd, "\n#\n", 3);
if (result != 3)
success = 0;
do {
result = read(mbr_audio_fd, dummybuf, sizeof(dummybuf));
} while (result > 0);
if (result != -1 || errno != EAGAIN)
success = 0;
if (!mbrola_has_errors() && success)
mbr_state = MBR_IDLE;
return success;
}
int read_MBR(void *buffer, int nb_samples)
{
int result = receive_from_mbrola(buffer, nb_samples * 2);
if (result > 0)
result /= 2;
return result;
}
int write_MBR(const char *data)
{
mbr_state = MBR_NEWDATA;
return send_to_mbrola(data);
}
int flush_MBR(void)
{
return send_to_mbrola("\n#\n") == 3;
}
int getFreq_MBR(void)
{
return mbr_samplerate;
}
void setVolumeRatio_MBR(float value)
{
if (value == mbr_volume)
return;
mbr_volume = value;
if (mbr_state != MBR_IDLE)
return;
/*
* We have no choice but to kill and restart mbrola with
* the new argument here.
*/
stop_mbrola();
init_MBR(mbr_voice_path);
}
int lastErrorStr_MBR(char *buffer, int bufsize)
{
int result = snprintf(buffer, bufsize, "%s", mbr_errorbuf);
return result >= bufsize ? (bufsize - 1) : result;
}
void resetError_MBR(void)
{
mbr_errorbuf[0] = 0;
}
+108
View File
@@ -0,0 +1,108 @@
/*
* mbrowrap -- A wrapper library around the mbrola binary
* providing a subset of the API from the Windows mbrola DLL.
*
* Copyright (C) 2010 by Nicolas Pitre <nico@fluxnic.net>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef MBROWRAP_H
#define MBROWRAP_H
#ifdef __cplusplus
extern "C"
{
#endif
/*
* Initialize mbrola. The 'voice_path' argument must contain the
* path and file name to the mbrola voice database to be used. Returned
* value is 0 on success, or an error code otherwise (currently only -1
* is returned. If not successful, lastErrorStr_MBR() will provide the
* error reason. If this is successful, then close_MBR() must be called
* before init_MBR() can be called again.
*/
int init_MBR(const char *voice_path);
/*
* Stop mbrola and release any resources. It is necessary to call
* this after a successful call to init_MBR() before init_MBR() can be
* called again.
*/
void close_MBR(void);
/*
* Stop any ongoing processing and flush all buffers. After this call
* any synthesis request will start afresh. A non-zero value is returned
* on success, or 0 on failure. If not successful, lastErrorStr_MBR() will
* provide the error reason.
*/
int reset_MBR();
/*
* Return at most 'nb_samples' audio samples into 'buffer'. The returned
* value is the actual number of samples returned, or -1 on error.
* If not successful, lastErrorStr_MBR() will provide the error reason.
* Samples are always 16-bit little endian.
*/
int read_MBR(void *buffer, int nb_samples);
/*
* Write a NULL terminated string of phoneme in the input buffer.
* Return the number of chars actually written, or -1 on error.
* If not successful, lastErrorStr_MBR() will provide the error reason.
*/
int write_MBR(const char *data);
/*
* Send a flush command to the mbrola input stream.
* This is currently similar to write_MBR("#\n"). Return 1 on success
* or 0 on failure. If not successful, lastErrorStr_MBR() will provide
* the error reason.
*/
int flush_MBR(void);
/*
* Return the audio sample frequency of the used voice database.
*/
int getFreq_MBR(void);
/*
* Overall volume.
*/
void setVolumeRatio_MBR(float value);
/*
* Copy into 'buffer' at most 'bufsize' bytes from the latest error
* message. This may also contain non-fatal errors from mbrola. The
* returned value is the actual number of bytes copied. When no error
* message is pending then an empty string is returned. Consecutive
* calls to lastErrorStr_MBR() will return the same message unless it
* is explicitly cleared with resetError_MBR().
*/
int lastErrorStr_MBR(char *buffer, int bufsize);
/*
* Clear any pending error message.
*/
void resetError_MBR(void);
/*
* Tolerance to missing diphones (always active so this is ignored)
*/
static inline void setNoError_MBR(int no_error) { }
#ifdef __cplusplus
}
#endif
#endif
-41
View File
@@ -140,7 +140,6 @@ void SetSpeed(int control)
int s1;
int wpm;
int wpm2;
int test=0;
speed.loud_consonants = 0;
speed.min_sample_len = 450;
@@ -172,43 +171,6 @@ void SetSpeed(int control)
speed.loud_consonants = (wpm - 360) / 8;
}
#ifdef deleted
if(wpm >= 450)
{
// TEST
speed1 = 6;
speed2 = speed3 = 5;
speed.pause_factor = 12;
speed.clause_pause_factor = 15;
speed.wav_factor = 70;
speed.lenmod_factor = 53;
speed.min_sample_len = 400;
return;
}
if(wpm > 390)
{
// TEST
speed1 = 6;
speed2 = speed3 = 5;
speed.pause_factor = 13;
speed.clause_pause_factor = 15;
if(wpm >= 440)
{
speed.wav_factor = 72 - (wpm - 440)/4;
speed.lenmod_factor = 60 - (wpm - 440)/2;
speed.min_sample_len = 420 - (wpm - 440);
}
else
{
speed.wav_factor = 74;
speed.lenmod_factor = 65 - (wpm - 400)/10;
speed.min_sample_len = 450 - (wpm - 400)/2;
}
return;
}
#endif
wpm2 = wpm;
if(wpm > 359) wpm2 = 359;
if(wpm < 80) wpm2 = 80;
@@ -269,9 +231,6 @@ void SetSpeed(int control)
speed.min_sample_len = 420 - (wpm - 440);
}
if(test > 0)
speed.wav_factor = test;
speed.pause_factor = (256 * s1)/115; // full speed adjustment, used for pause length
speed.clause_pause_factor = 0;
+12 -3
View File
@@ -98,8 +98,10 @@ static const char *help_text =
"\t directory. <voice name> specifies the language\n"
"--path=\"<path>\"\n"
"\t Specifies the directory containing the espeak-data directory\n"
"--pho\n"
"\t Write mbrola phoneme data (.pho) to stdout, or to the file in --phonout\n"
"--phonout=\"<filename>\"\n"
"\t Write output from -x -X commands, and mbrola phoneme data, to this file\n"
"\t Write phoneme output from -x -X and --pho to this file\n"
"--punct=\"<characters>\"\n"
"\t Speak the names of punctuation characters during speaking. If\n"
"\t =<characters> is omitted, all punctuation is spoken.\n"
@@ -214,7 +216,9 @@ void DisplayVoices(FILE *f_out, char *language)
} // end of DisplayVoices
void WVoiceChanged(voice_t *wvoice)
{
}
static int OpenWaveFile(const char *path, int rate)
//=================================================
@@ -472,7 +476,8 @@ int main (int argc, char **argv)
{"stdout", no_argument, 0, 0x105},
{"split", optional_argument, 0, 0x106},
{"path", required_argument, 0, 0x107},
{"phonout", required_argument, 0, 0x108},
{"phonout", required_argument, 0, 0x108},
{"pho", no_argument, 0, 0x109},
{0, 0, 0, 0}
};
@@ -702,6 +707,10 @@ int main (int argc, char **argv)
}
break;
case 0x109: // --pho
option_mbrola_phonemes = 8;
break;
default:
exit(0);
}
+49 -10
View File
@@ -59,6 +59,9 @@ static unsigned int my_unique_identifier=0;
static void* my_user_data=NULL;
static espeak_AUDIO_OUTPUT my_mode=AUDIO_OUTPUT_SYNCHRONOUS;
static int synchronous_mode = 1;
static int out_samplerate = 0;
static int voice_samplerate = 22050;
t_espeak_callback* synth_callback = NULL;
int (* uri_callback)(int, const char *, const char *) = NULL;
int (* phoneme_callback)(const char *) = NULL;
@@ -66,6 +69,13 @@ int (* phoneme_callback)(const char *) = NULL;
char path_home[N_PATH_HOME]; // this is the espeak-data directory
void WVoiceChanged(voice_t *wvoice)
{//=================================
// Voice change in wavegen
voice_samplerate = wvoice->samplerate;
}
#ifdef USE_ASYNC
static int dispatch_audio(short* outbuf, int length, espeak_EVENT* event)
@@ -85,6 +95,34 @@ static int dispatch_audio(short* outbuf, int length, espeak_EVENT* event)
{
case AUDIO_OUTPUT_PLAYBACK:
{
int event_type=0;
int event_data=0;
if(event)
{
event_type = event->type;
event_data = event->id.number;
}
if(event_type == espeakEVENT_SAMPLERATE)
{
voice_samplerate = event->id.number;
if(out_samplerate != voice_samplerate)
{
if(out_samplerate != 0)
{
// sound was previously open with a different sample rate
wave_close(my_audio);
sleep(1);
}
out_samplerate = voice_samplerate;
wave_init(voice_samplerate);
wave_set_callback_is_output_enabled( fifo_is_command_enabled);
my_audio = wave_open("alsa");
event_init();
}
}
if (outbuf && length && a_wave_can_be_played)
{
wave_write (my_audio, (char*)outbuf, 2*length);
@@ -220,17 +258,13 @@ static void select_output(espeak_AUDIO_OUTPUT output_type)
my_audio = NULL;
synchronous_mode = 1;
option_waveout = 1; // inhibit portaudio callback from wavegen.cpp
out_samplerate = 0;
switch(my_mode)
{
case AUDIO_OUTPUT_PLAYBACK:
// wave_init() is now called just before the first wave_write()
synchronous_mode = 0;
#ifdef USE_ASYNC
wave_init();
wave_set_callback_is_output_enabled( fifo_is_command_enabled);
my_audio = wave_open("alsa");
event_init();
#endif
break;
case AUDIO_OUTPUT_RETRIEVAL:
@@ -734,19 +768,21 @@ ENTER("espeak_Initialize");
return(EE_INTERNAL_ERROR);
option_phonemes = 0;
option_mbrola_phonemes = 0;
option_phoneme_events = (options & 1);
SetVoiceByName("default");
VoiceReset(0);
// SetVoiceByName("default");
for(param=0; param<N_SPEECH_PARAM; param++)
param_stack[0].parameter[param] = param_defaults[param];
SetParameter(espeakRATE,170,0);
SetParameter(espeakRATE,175,0);
SetParameter(espeakVOLUME,100,0);
SetParameter(espeakCAPITALS,option_capitals,0);
SetParameter(espeakPUNCTUATION,option_punctuation,0);
SetParameter(espeakWORDGAP,0,0);
DoVoiceChange(voice);
// DoVoiceChange(voice);
#ifdef USE_ASYNC
fifo_init();
@@ -1087,8 +1123,10 @@ ESPEAK_API void espeak_SetPhonemeTrace(int value, FILE *stream)
value=0 No phoneme output (default)
value=1 Output the translated phoneme symbols for the text
value=2 as (1), but also output a trace of how the translation was done (matching rules and list entries)
bit 3: produce mbrola pho data
*/
option_phonemes = value;
option_phonemes = value & 3;
option_mbrola_phonemes = value & 8;
f_trans = stream;
if(stream == NULL)
f_trans = stderr;
@@ -1163,6 +1201,7 @@ ESPEAK_API espeak_ERROR espeak_Terminate(void)
{
wave_close(my_audio);
wave_terminate();
out_samplerate = 0;
}
#endif
+7 -6
View File
@@ -50,12 +50,13 @@ Revision 5
typedef enum {
espeakEVENT_LIST_TERMINATED = 0, // Retrieval mode: terminates the event list.
espeakEVENT_WORD = 1, // Start of word
espeakEVENT_SENTENCE, // Start of sentence
espeakEVENT_MARK, // Mark
espeakEVENT_PLAY, // Audio element
espeakEVENT_END, // End of sentence or clause
espeakEVENT_MSG_TERMINATED, // End of message
espeakEVENT_PHONEME // Phoneme, if enabled in espeak_Initialize()
espeakEVENT_SENTENCE = 2, // Start of sentence
espeakEVENT_MARK = 3, // Mark
espeakEVENT_PLAY = 4, // Audio element
espeakEVENT_END = 5, // End of sentence or clause
espeakEVENT_MSG_TERMINATED = 6, // End of message
espeakEVENT_PHONEME = 7, // Phoneme, if enabled in espeak_Initialize()
espeakEVENT_SAMPLERATE = 8 // internal use, set sample rate
} espeak_EVENT_TYPE;
-1
View File
@@ -44,7 +44,6 @@
#ifdef LIBRARY
#define USE_ASYNC
//#define USE_MBROLA_LIB
#endif
#ifdef _ESPEAKEDIT
+104 -229
View File
@@ -35,15 +35,11 @@
extern int Read4Bytes(FILE *f);
extern void SetPitch2(voice_t *voice, int pitch1, int pitch2, int *pitch_base, int *pitch_range);
#ifdef USE_MBROLA_LIB
extern unsigned char *outbuf;
#ifndef PLATFORM_WINDOWS
#include "mbrolib.h"
void * mb_handle;
#include "mbrowrap.h"
#else
#include <windows.h>
@@ -64,7 +60,7 @@ PROCVV reset_MBR;
PROCIV lastError_MBR;
PROCVCI lastErrorStr_MBR;
PROCVI setNoError_MBR;
PROCVI setFreq_MBR;
PROCIV getFreq_MBR;
PROCVF setVolumeRatio_MBR;
@@ -103,13 +99,11 @@ void unload_MBR()
}
#endif // windows
#endif // USE_MBROLA_LIB
static MBROLA_TAB *mbrola_tab = NULL;
static int mbrola_control = 0;
int option_mbrola_phonemes;
espeak_ERROR LoadMbrolaTable(const char *mbrola_voice, const char *phtrans, int srate)
@@ -133,37 +127,35 @@ espeak_ERROR LoadMbrolaTable(const char *mbrola_voice, const char *phtrans, int
}
sprintf(path,"%s/mbrola/%s",path_home,mbrola_voice);
#ifdef USE_MBROLA_LIB
#ifdef PLATFORM_POSIX
if(GetFileLength(path) <= 0)
{
// mbrola voice file not found, look in /usr/share
sprintf(path,"/usr/share/mbrola/%s",mbrola_voice);
}
#endif
#ifdef PLATFORM_WINDOWS
if(load_MBR() == FALSE) // load mbrola.dll
return(EE_INTERNAL_ERROR);
#endif
if(init_MBR(path) != 0) // initialise the required mbrola voice
return(EE_NOT_FOUND);
setNoError_MBR(1); // don't stop on phoneme errors
#else
mb_handle = mbrolib_init(srate);
mbrolib_parameter m_parameters;
if(mb_handle == NULL)
return(EE_INTERNAL_ERROR);
MBROLIB_ERROR a_status = mbrolib_set_voice(mb_handle, mbrola_voice);
if(a_status != MBROLIB_OK)
return(EE_NOT_FOUND);
#endif // not windows
#endif // USE_MBROLA_LIB
// read eSpeak's mbrola phoneme translation data, eg. en1_phtrans
sprintf(path,"%s/mbrola_ph/%s",path_home,phtrans);
size = GetFileLength(path);
if((f_in = fopen(path,"r")) == NULL)
if((f_in = fopen(path,"r")) == NULL) {
close_MBR();
return(EE_NOT_FOUND);
}
if((mbrola_tab = (MBROLA_TAB *)realloc(mbrola_tab,size)) == NULL)
{
fclose(f_in);
close_MBR();
return(EE_INTERNAL_ERROR);
}
@@ -176,26 +168,16 @@ espeak_ERROR LoadMbrolaTable(const char *mbrola_voice, const char *phtrans, int
fread(mbrola_tab,size,1,f_in);
fclose(f_in);
#ifdef USE_MBROLA_LIB
#ifdef PLATFORM_WINDOWS
setVolumeRatio_MBR((float)(mbrola_control & 0xff) /16.0f);
#else
mbrolib_get_parameter(mb_handle,&m_parameters);
m_parameters.ignore_error = 1;
m_parameters.volume_ratio = (float)(mbrola_control & 0xff) /16.0;
mbrolib_set_parameter(mb_handle,&m_parameters);
#endif // not windows
#endif // USE_MBROLA_LIB
option_quiet = 1;
// srate = getFreq_MBR();
samplerate = srate;
if(srate == 22050)
SetParameter(espeakVOICETYPE,0,0);
else
SetParameter(espeakVOICETYPE,1,0);
strcpy(mbrola_name,mbrola_voice);
mbrola_delay = 3800; // improve synchronization of events
// mbrola_delay = 3800; // improve synchronization of events
mbrola_delay = 1000; // improve synchronization of events
return(EE_OK);
} // end of LoadMbrolaTable
@@ -383,155 +365,10 @@ static char *WritePitch(int env, int pitch1, int pitch2, int split, int final)
} // end of WritePitch
#ifdef USE_MBROLA_LIB
static void MbrolaMarker(int type, int char_posn, int length, int value)
{//=====================================================================
MarkerEvent(type,(char_posn & 0xffffff) | (length << 24),value,outbuf);
}
static void MbrolaEmbedded(int &embix, int sourceix)
{//=================================================
// There were embedded commands in the text at this point
unsigned int word; // bit 7=last command for this word, bits 5,6 sign, bits 0-4 command
unsigned int value;
int command;
int sign=0;
do {
word = embedded_list[embix++];
value = word >> 8;
command = word & 0x1f;
if((word & 0x60) == 0x60)
sign = -1;
else
if((word & 0x60) == 0x40)
sign = 1;
if(command < N_EMBEDDED_VALUES)
{
if(sign == 0)
embedded_value[command] = value;
else
embedded_value[command] += (value * sign);
}
switch(command & 0x1f)
{
case EMBED_M: // named marker
MbrolaMarker(espeakEVENT_MARK, (sourceix & 0x7ff) + clause_start_char, 0, value);
break;
}
} while ((word & 0x80) == 0);
}
#ifdef PLATFORM_WINDOWS
static int MbrolaSynth(char *p_mbrola)
{//===================================
// p_mbrola is a string of mbrola pho lines - Windows
int len;
int finished;
int result=0;
if(synth_callback == NULL)
return(1);
if(p_mbrola == NULL)
flush_MBR();
else
result = write_MBR(p_mbrola);
finished = 0;
while(!finished && ((len = read_MBR((short *)outbuf, outbuf_size/2)) > 0))
{
out_ptr = outbuf + len*2;
if(event_list)
{
event_list[event_list_ix].type = espeakEVENT_LIST_TERMINATED; // indicates end of event list
event_list[event_list_ix].user_data = 0;
}
count_samples += len;
finished = synth_callback((short *)outbuf, len, event_list);
event_list_ix=0;
}
if(finished)
{
// cancelled by user, discard any unused mbrola speech
flush_MBR();
while((len = read_MBR((short *)outbuf, outbuf_size/2)) > 0);
}
return(finished);
} // end of SynthMbrola
#else
static int MbrolaSynth(char *p_mbrola)
{//===================================
// p_mbrola is a string of mbrola pho lines - Linux
// This is wrong
// It must be called from WavegenFill()
int len;
int finished;
int result=0;
if(synth_callback == NULL)
return(1);
if(p_mbrola == NULL)
mbrolib_flush(mb_handle);
else
result = mbrolib_write(mb_handle,p_mbrola,strlen(p_mbrola));
finished = 0;
while(!finished && (mbrolib_read(mb_handle, (short *)out_ptr, (out_end - out_ptr)/2, &len) == MBROLIB_OK))
{
if(len == 0)
break;
out_ptr += (len*2);
if(event_list)
{
event_list[event_list_ix].type = espeakEVENT_LIST_TERMINATED; // indicates end of event list
event_list[event_list_ix].user_data = 0;
}
count_samples += len;
finished = synth_callback((short *)outbuf, len, event_list);
event_list_ix=0;
}
if(finished)
{
// cancelled by user, discard any unused mbrola speech
mbrolib_flush(mb_handle);
while(mbrolib_read(mb_handle, (short *)outbuf, outbuf_size/2, &len) == MBROLIB_OK)
{
if(len == 0)
break;
}
}
return(finished);
} // end of SynthMbrola
#endif // not windows
#endif // USE_MBROLA_LIB
void MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, FILE *f_mbrola)
{//======================================================================
int MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, int resume, FILE *f_mbrola)
{//=================================================================================
// Generate a mbrola pho file
unsigned int name;
int phix;
int len;
int len1;
PHONEME_TAB *ph;
@@ -552,21 +389,21 @@ void MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, FILE *f_mbrola)
char buf[80];
char mbr_buf[120];
#ifdef USE_MBROLA_LIB
int embedded_ix=0;
int word_count=0;
static int phix;
static int embedded_ix;
static int word_count;
event_list_ix = 0;
out_ptr = outbuf;
#ifdef PLATFORM_WINDOWS
setNoError_MBR(1); // don't stop on phoneme errors
#endif
#else
// fprintf(f_mbrola,";; v=%.2f\n",(float)(mbrola_control & 0xff)/16.0); // ;; v= has no effect on mbrola
#endif
if (!resume) {
phix = 1;
embedded_ix = 0;
word_count = 0;
}
for(phix=1; phix < n_phonemes; phix++)
while (phix < n_phonemes)
{
if (WcmdqFree() < MIN_WCMDQ)
return 1;
mbr_buf[0] = 0;
p = &plist[phix];
@@ -576,24 +413,24 @@ void MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, FILE *f_mbrola)
ph_prev = plist[phix-1].ph;
ph_next = plist[phix+1].ph;
#ifdef USE_MBROLA_LIB
if(p->synthflags & SFLAG_EMBEDDED)
{
MbrolaEmbedded(embedded_ix, p->sourceix);
DoEmbedded(embedded_ix, p->sourceix);
}
if(p->newword & 4)
MbrolaMarker(espeakEVENT_SENTENCE, (p->sourceix & 0x7ff) + clause_start_char, 0, count_sentences);
if(p->newword & 4)
DoMarker(espeakEVENT_SENTENCE, (p->sourceix & 0x7ff) + clause_start_char, 0, count_sentences);
if(p->newword & 1)
MbrolaMarker(espeakEVENT_WORD, (p->sourceix & 0x7ff) + clause_start_char, p->sourceix >> 11, clause_start_word + word_count++);
#endif
DoMarker(espeakEVENT_WORD, (p->sourceix & 0x7ff) + clause_start_char, p->sourceix >> 11, clause_start_word + word_count++);
name = GetMbrName(p,ph,ph_prev,ph_next,&name2,&len_percent,&control);
if(control & 1)
phix++;
if(name == 0)
if(name == 0) {
phix++;
continue; // ignore this phoneme
}
if((ph->type == phPAUSE) && (name == ph->mnemonic))
{
@@ -607,9 +444,7 @@ void MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, FILE *f_mbrola)
else
len = (80 * speed.wav_factor)/256;
#ifdef USE_MBROLA_LIB
MbrolaMarker(espeakEVENT_PHONEME, (p->sourceix & 0x7ff) + clause_start_char, 0, ph->mnemonic);
#endif
DoMarker(espeakEVENT_PHONEME, (p->sourceix & 0x7ff) + clause_start_char, 0, ph->mnemonic);
sprintf(buf,"%s\t",WordToString(name));
strcat(mbr_buf,buf);
@@ -720,6 +555,7 @@ void MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, FILE *f_mbrola)
if(pause)
{
len += PauseLength(pause,0);
sprintf(buf,"_ \t%d\n",PauseLength(pause,0));
strcat(mbr_buf,buf);
pause = 0;
@@ -731,39 +567,78 @@ void MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, FILE *f_mbrola)
}
else
{
#ifdef USE_MBROLA_LIB
if(MbrolaSynth(mbr_buf) != 0)
return;
#endif
int res = write_MBR(mbr_buf);
if (res < 0)
return 0; /* don't get stuck on error */
if (res == 0)
return 1;
wcmdq[wcmdq_tail][0] = WCMD_MBROLA_DATA;
wcmdq[wcmdq_tail][1] = len;
WcmdqInc();
}
phix++;
}
#ifdef USE_MBROLA_LIB
MbrolaSynth(NULL);
#endif
if(!f_mbrola)
{
flush_MBR();
// flush the mbrola output buffer
wcmdq[wcmdq_tail][0] = WCMD_MBROLA_DATA;
wcmdq[wcmdq_tail][1] = 500;
WcmdqInc();
}
return 0;
} // end of MbrolaTranslate
#ifdef TEST_MBROLA
static PHONEME_LIST mbrola_phlist;
static int mbrola_n_ph;
static int mbrola_phix;
int MbrolaFill(int fill_zeros)
{//===========================
}
int MbrolaGenerate(PHONEME_LIST *phoneme_list, int *n_ph, int resume)
{//==================================================================
if(resume == 0)
FILE *f_mbrola = NULL;
if(*n_ph == 0)
return(0);
if(option_mbrola_phonemes)
{
mbrola_phlist = phoneme_list;
mbrola_n_ph = n_ph;
mbrola_phix = 0;
// send mbrola data to a file, not to the mbrola library
f_mbrola = f_trans;
}
resume(0); // finished phoneme list
int again = MbrolaTranslate(phoneme_list, *n_ph, resume, f_mbrola);
if (!again)
*n_ph = 0;
return again;
}
int MbrolaFill(int length, int resume)
{//===================================
// Read audio data from Mbrola (length is in milisecs)
static int n_samples;
int req_samples, result;
if (!resume)
n_samples = samplerate * length / 1000;
req_samples = (out_end - out_ptr)/2;
if (req_samples > n_samples)
req_samples = n_samples;
result = read_MBR((short *)out_ptr, req_samples);
if (result <= 0)
return 0;
out_ptr += result*2;
n_samples -= result;
return n_samples ? 1 : 0;
}
void MbrolaReset(void)
{//===================
// Reset the Mbrola engine and flush the pending audio
reset_MBR();
}
#endif
+1 -1
View File
@@ -35,7 +35,7 @@
#include "translate.h"
#include "wave.h"
const char *version_string = "1.43.46 20.Jun.10";
const char *version_string = "1.43.48 28.Jun.10";
const int version_phdata = 0x014342;
int option_device_number = -1;
+15 -57
View File
@@ -135,7 +135,7 @@ static void EndPitch(int voice_break)
syllable_centre = -1;
memset(vowel_transition,0,sizeof(vowel_transition));
}
} // end of Synthesize::EndPitch
} // end of EndPitch
@@ -152,7 +152,7 @@ static void DoAmplitude(int amp, unsigned char *amp_env)
q[2] = (long)amp_env;
q[3] = amp;
WcmdqInc();
} // end of Synthesize::DoAmplitude
} // end of DoAmplitude
@@ -181,7 +181,7 @@ static void DoPitch(unsigned char *env, int pitch1, int pitch2)
q[2] = (long)env;
q[3] = (pitch1 << 16) + pitch2;
WcmdqInc();
} // end of Synthesize::DoPitch
} // end of DoPitch
@@ -223,7 +223,7 @@ static void DoPause(int length, int control)
wcmdq[wcmdq_tail][1] = len;
WcmdqInc();
last_frame = NULL;
} // end of Synthesize::DoPause
} // end of DoPause
extern int seq_len_adjust; // temporary fix to advance the start point for playing the wav sample
@@ -253,9 +253,9 @@ static int DoSample2(int index, int which, int std_length, int control, int leng
else
{
// increase consonant amplitude at high speeds, depending on the peak consonant amplitude
x = ((35 - wav_scale) * speed.loud_consonants);
if(x < 0) x = 0;
wav_scale = (wav_scale * (x+256))/256;
// x = ((35 - wav_scale) * speed.loud_consonants);
// if(x < 0) x = 0;
// wav_scale = (wav_scale * (x+256))/256;
}
if(std_length > 0)
@@ -383,32 +383,6 @@ static int DoSample2(int index, int which, int std_length, int control, int leng
} // end of DoSample2
#ifdef deleted
int DoSample(PHONEME_TAB *ph1, PHONEME_TAB *ph2, int which, int length_mod, int amp)
{//====================== ==========================================================
int index;
int match_level;
int amp2;
int result;
EndPitch(1);
index = LookupSound(ph1,ph2,which & 0xff,&match_level,0);
if((index & 0x800000) == 0)
return(0); // not wavefile data
amp2 = wavefile_amp;
if(amp != 0)
amp2 = (amp * wavefile_amp)/20;
if(amp == -1)
amp2 = amp;
result = DoSample2(index,which,length_mod,0,amp2);
last_frame = NULL;
return(result);
} // end of DoSample
#endif
int DoSample3(PHONEME_DATA *phdata, int length_mod, int amp)
{//=========================================================
@@ -1198,8 +1172,8 @@ if(which==1)
static void DoMarker(int type, int char_posn, int length, int value)
{//=================================================================
void DoMarker(int type, int char_posn, int length, int value)
{//==========================================================
// This could be used to return an index to the word currently being spoken
// Type 1=word, 2=sentence, 3=named marker, 4=play audio, 5=end
wcmdq[wcmdq_tail][0] = WCMD_MARKER;
@@ -1208,7 +1182,7 @@ static void DoMarker(int type, int char_posn, int length, int value)
wcmdq[wcmdq_tail][3] = value;
WcmdqInc();
} // end of Synthesize::DoMarker
} // end of DoMarker
void DoVoiceChange(voice_t *v)
@@ -1224,8 +1198,8 @@ void DoVoiceChange(voice_t *v)
}
static void DoEmbedded(int &embix, int sourceix)
{//=============================================
void DoEmbedded(int &embix, int sourceix)
{//======================================
// There were embedded commands in the text at this point
unsigned int word; // bit 7=last command for this word, bits 5,6 sign, bits 0-4 command
unsigned int value;
@@ -1305,14 +1279,12 @@ int Generate(PHONEME_LIST *phoneme_list, int *n_ph, int resume)
PHONEME_DATA phdata_tone;
FMT_PARAMS fmtp;
#ifdef TEST_MBROLA
if(mbrola_name[0] != 0)
return(MbrolaGenerate(phoneme_list,n_ph,resume));
#endif
if(option_quiet)
return(0);
if(mbrola_name[0] != 0)
return(MbrolaGenerate(phoneme_list,n_ph,resume));
if(resume == 0)
{
ix = 1;
@@ -1899,20 +1871,6 @@ int SpeakNextClause(FILE *f_in, const void *text_in, int control)
return(1);
}
if(mbrola_name[0] != 0)
{
#ifdef USE_MBROLA_LIB
MbrolaTranslate(phoneme_list,n_phoneme_list,NULL);
#else
{
FILE *f_mbrola;
if((f_mbrola = f_trans) == stderr)
f_mbrola = stdout;
MbrolaTranslate(phoneme_list,n_phoneme_list,f_mbrola);
}
#endif
}
Generate(phoneme_list,&n_phoneme_list,0);
WavegenOpenSound();
+7 -2
View File
@@ -462,6 +462,7 @@ extern unsigned char pitch_adjust_tab[MAX_PITCH_VALUE+1];
#define WCMD_MARKER 10
#define WCMD_VOICE 11
#define WCMD_EMBEDDED 12
#define WCMD_MBROLA_DATA 13
#define N_WCMDQ 160
@@ -557,8 +558,12 @@ espeak_ERROR SetVoiceByName(const char *name);
espeak_ERROR SetVoiceByProperties(espeak_VOICE *voice_selector);
espeak_ERROR LoadMbrolaTable(const char *mbrola_voice, const char *phtrans, int srate);
void SetParameter(int parameter, int value, int relative);
void MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, FILE *f_mbrola);
//int MbrolaSynth(char *p_mbrola);
int MbrolaTranslate(PHONEME_LIST *plist, int n_phonemes, int resume, FILE *f_mbrola);
int MbrolaGenerate(PHONEME_LIST *phoneme_list, int *n_ph, int resume);
int MbrolaFill(int length, int resume);
void MbrolaReset(void);
void DoEmbedded(int &embix, int sourceix);
void DoMarker(int type, int char_posn, int length, int value);
//int DoSample(PHONEME_TAB *ph1, PHONEME_TAB *ph2, int which, int length_mod, int amp);
int DoSample3(PHONEME_DATA *phdata, int length_mod, int amp);
int DoSpect2(PHONEME_TAB *this_ph, int which, FMT_PARAMS *fmt_params, PHONEME_LIST *plist, int modulation);
-21
View File
@@ -1,21 +0,0 @@
/***************************************************************************
* Copyright (C) 2005 to 2007 by Jonathan Duddington *
* email: jonsd@users.sourceforge.net *
* *
* This program is free software; you can redistribute it and/or modify *
* it under the terms of the GNU General Public License as published by *
* the Free Software Foundation; either version 3 of the License, or *
* (at your option) any later version. *
* *
* This program is distributed in the hope that it will be useful, *
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
* GNU General Public License for more details. *
* *
* You should have received a copy of the GNU General Public License *
* along with this program; if not, write see: *
* <http://www.gnu.org/licenses/>. *
***************************************************************************/
#include "StdAfx.h"
-1
View File
@@ -881,7 +881,6 @@ SetLengthMods(tr,3); // all equal
static const short stress_lengths_nl[8] = {160,135, 210,210, 0, 0, 260,280};
tr->langopts.stress_rule = STRESSPOSN_1L;
tr->langopts.vowel_pause = 1;
tr->langopts.vowel_pause = 0x30; // ??
tr->langopts.param[LOPT_DIERESES] = 1;
tr->langopts.param[LOPT_PREFIXES] = 1;
+1
View File
@@ -545,6 +545,7 @@ extern int option_tone_flags;
extern int option_waveout;
extern int option_quiet;
extern int option_phonemes;
extern int option_mbrola_phonemes;
extern int option_phoneme_events;
extern int option_linelength; // treat lines shorter than this as end-of-clause
extern int option_multibyte;
+3
View File
@@ -41,6 +41,7 @@ typedef struct {
int formant_factor; // adjust nominal formant frequencies by this because of the voice's pitch (256ths)
int consonant_amp; // amplitude of unvoiced consonants
int consonant_ampv; // amplitude of the noise component of voiced consonants
int samplerate;
int klattv[8];
// parameters used by Wavegen
@@ -77,6 +78,8 @@ espeak_VOICE *SelectVoiceByName(espeak_VOICE **voices, const char *name);
voice_t *LoadVoice(const char *voice_name, int control);
voice_t *LoadVoiceVariant(const char *voice_name, int variant);
void DoVoiceChange(voice_t *v);
void WVoiceChanged(voice_t *wvoice);
void WavegenSetVoice(voice_t *v);
void ReadTonePoints(char *string, int *tone_pts);
void VoiceReset(int control);
+2
View File
@@ -408,6 +408,7 @@ void VoiceReset(int tone_only)
voice->voicing = 64;
voice->consonant_amp = 100;
voice->consonant_ampv = 100;
voice->samplerate = 22050;
memset(voice->klattv,0,sizeof(voice->klattv));
memset(speed.fast_settings,0,sizeof(speed.fast_settings));
@@ -921,6 +922,7 @@ voice_t *LoadVoice(const char *vname, int control)
phtrans[0] = 0;
sscanf(p,"%s %s %d",name,phtrans,&srate);
LoadMbrolaTable(name,phtrans,srate);
voice->samplerate = srate;
}
break;
+93 -91
View File
@@ -56,15 +56,16 @@ enum {ONE_BILLION=1000000000};
static t_wave_callback* my_callback_is_output_enabled=NULL;
#define N_WAV_BUF 10
#define SAMPLE_RATE 22050
#define MAX_SAMPLE_RATE 22050
#define FRAMES_PER_BUFFER 512
#define BUFFER_LENGTH (SAMPLE_RATE*2*sizeof(uint16_t))
#define THRESHOLD (BUFFER_LENGTH/5)
#define BUFFER_LENGTH (MAX_SAMPLE_RATE*2*sizeof(uint16_t))
//#define THRESHOLD (BUFFER_LENGTH/5)
static char myBuffer[BUFFER_LENGTH];
static char* myRead=NULL;
static char* myWrite=NULL;
static int out_channels=1;
static int my_stream_could_start=0;
static int wave_samplerate;
static int mInCallbackFinishedState = false;
#if (USE_PORTAUDIO == 18)
@@ -168,89 +169,89 @@ static int pa_callback(void *inputBuffer, void *outputBuffer,
PaStreamCallbackFlags flags, void *userData )
#endif
{
int aResult=0; // paContinue
char* aWrite = myWrite;
size_t n = out_channels*sizeof(uint16_t)*framesPerBuffer;
int aResult=0; // paContinue
char* aWrite = myWrite;
size_t n = out_channels*sizeof(uint16_t)*framesPerBuffer;
myReadPosition += framesPerBuffer;
SHOW("pa_callback > myReadPosition=%u, framesPerBuffer=%lu (n=0x%x) \n",(int)myReadPosition, framesPerBuffer, n);
myReadPosition += framesPerBuffer;
SHOW("pa_callback > myReadPosition=%u, framesPerBuffer=%lu (n=0x%x) \n",(int)myReadPosition, framesPerBuffer, n);
if (aWrite >= myRead)
{
if((size_t)(aWrite - myRead) >= n)
if (aWrite >= myRead)
{
memcpy(outputBuffer, myRead, n);
myRead += n;
if((size_t)(aWrite - myRead) >= n)
{
memcpy(outputBuffer, myRead, n);
myRead += n;
}
else
{
SHOW_TIME("pa_callback > underflow");
aResult=1; // paComplete;
mInCallbackFinishedState = true;
size_t aUsedMem=0;
aUsedMem = (size_t)(aWrite - myRead);
if (aUsedMem)
{
memcpy(outputBuffer, myRead, aUsedMem);
}
char* p = (char*)outputBuffer + aUsedMem;
memset(p, 0, n - aUsedMem);
// myReadPosition += aUsedMem/(out_channels*sizeof(uint16_t));
myRead = aWrite;
}
}
else
else // myRead > aWrite
{
SHOW_TIME("pa_callback > underflow");
aResult=1; // paComplete;
mInCallbackFinishedState = true;
size_t aUsedMem=0;
aUsedMem = (size_t)(aWrite - myRead);
if (aUsedMem)
{
memcpy(outputBuffer, myRead, aUsedMem);
}
char* p = (char*)outputBuffer + aUsedMem;
memset(p, 0, n - aUsedMem);
// myReadPosition += aUsedMem/(out_channels*sizeof(uint16_t));
myRead = aWrite;
}
}
else // myRead > aWrite
{
if ((size_t)(myBuffer + BUFFER_LENGTH - myRead) >= n)
{
memcpy(outputBuffer, myRead, n);
myRead += n;
}
else if ((size_t)(aWrite + BUFFER_LENGTH - myRead) >= n)
{
int aTopMem = myBuffer + BUFFER_LENGTH - myRead;
if (aTopMem)
{
SHOW("pa_callback > myRead=0x%x, aTopMem=0x%x\n",(int)myRead, (int)aTopMem);
memcpy(outputBuffer, myRead, aTopMem);
}
int aRest = n - aTopMem;
if (aRest)
{
SHOW("pa_callback > myRead=0x%x, aRest=0x%x\n",(int)myRead, (int)aRest);
char* p = (char*)outputBuffer + aTopMem;
memcpy(p, myBuffer, aRest);
}
myRead = myBuffer + aRest;
}
else
{
SHOW_TIME("pa_callback > underflow");
aResult=1; // paComplete;
if ((size_t)(myBuffer + BUFFER_LENGTH - myRead) >= n)
{
memcpy(outputBuffer, myRead, n);
myRead += n;
}
else if ((size_t)(aWrite + BUFFER_LENGTH - myRead) >= n)
{
int aTopMem = myBuffer + BUFFER_LENGTH - myRead;
if (aTopMem)
{
SHOW("pa_callback > myRead=0x%x, aTopMem=0x%x\n",(int)myRead, (int)aTopMem);
memcpy(outputBuffer, myRead, aTopMem);
}
int aRest = n - aTopMem;
if (aRest)
{
SHOW("pa_callback > myRead=0x%x, aRest=0x%x\n",(int)myRead, (int)aRest);
char* p = (char*)outputBuffer + aTopMem;
memcpy(p, myBuffer, aRest);
}
myRead = myBuffer + aRest;
}
else
{
SHOW_TIME("pa_callback > underflow");
aResult=1; // paComplete;
int aTopMem = myBuffer + BUFFER_LENGTH - myRead;
if (aTopMem)
{
SHOW("pa_callback > myRead=0x%x, aTopMem=0x%x\n",(int)myRead, (int)aTopMem);
memcpy(outputBuffer, myRead, aTopMem);
}
int aRest = aWrite - myBuffer;
if (aRest)
{
SHOW("pa_callback > myRead=0x%x, aRest=0x%x\n",(int)myRead, (int)aRest);
char* p = (char*)outputBuffer + aTopMem;
memcpy(p, myBuffer, aRest);
}
int aTopMem = myBuffer + BUFFER_LENGTH - myRead;
if (aTopMem)
{
SHOW("pa_callback > myRead=0x%x, aTopMem=0x%x\n",(int)myRead, (int)aTopMem);
memcpy(outputBuffer, myRead, aTopMem);
}
int aRest = aWrite - myBuffer;
if (aRest)
{
SHOW("pa_callback > myRead=0x%x, aRest=0x%x\n",(int)myRead, (int)aRest);
char* p = (char*)outputBuffer + aTopMem;
memcpy(p, myBuffer, aRest);
}
size_t aUsedMem = aTopMem + aRest;
char* p = (char*)outputBuffer + aUsedMem;
memset(p, 0, n - aUsedMem);
// myReadPosition += aUsedMem/(out_channels*sizeof(uint16_t));
myRead = aWrite;
size_t aUsedMem = aTopMem + aRest;
char* p = (char*)outputBuffer + aUsedMem;
memset(p, 0, n - aUsedMem);
// myReadPosition += aUsedMem/(out_channels*sizeof(uint16_t));
myRead = aWrite;
}
}
}
SHOW("pa_callback > myRead=%x\n",(int)myRead);
SHOW("pa_callback > myRead=%x\n",(int)myRead);
// #if USE_PORTAUDIO == 18
@@ -288,7 +289,7 @@ static int pa_callback(void *inputBuffer, void *outputBuffer,
#endif
return(aResult);
return(aResult);
//#endif
} // end of WaveCallBack
@@ -335,7 +336,7 @@ static int wave_open_sound()
out_channels = 1;
#if USE_PORTAUDIO == 18
// err = Pa_OpenDefaultStream(&pa_stream,0,1,paInt16,SAMPLE_RATE,FRAMES_PER_BUFFER,N_WAV_BUF,pa_callback,(void *)userdata);
// err = Pa_OpenDefaultStream(&pa_stream,0,1,paInt16,wave_samplerate,FRAMES_PER_BUFFER,N_WAV_BUF,pa_callback,(void *)userdata);
PaDeviceID playbackDevice = Pa_GetDefaultOutputDeviceID();
@@ -351,7 +352,7 @@ static int wave_open_sound()
paInt16,
NULL,
/* general parameters */
SAMPLE_RATE, FRAMES_PER_BUFFER, 0,
wave_samplerate, FRAMES_PER_BUFFER, 0,
//paClipOff | paDitherOff,
paNoFlag,
pa_callback, (void *)userdata);
@@ -376,12 +377,12 @@ static int wave_open_sound()
paInt16,
NULL,
/* general parameters */
SAMPLE_RATE, FRAMES_PER_BUFFER, 0,
wave_samplerate, FRAMES_PER_BUFFER, 0,
//paClipOff | paDitherOff,
paNoFlag,
pa_callback, (void *)userdata);
// err = Pa_OpenDefaultStream(&pa_stream,0,2,paInt16,
// SAMPLE_RATE,
// wave_samplerate,
// FRAMES_PER_BUFFER,
// N_WAV_BUF,pa_callback,(void *)userdata);
SHOW("wave_open_sound > Pa_OpenDefaultStream(2): err=%d (%s)\n",err, Pa_GetErrorText(err));
@@ -395,7 +396,7 @@ static int wave_open_sound()
&pa_stream,
NULL, /* no input */
&myOutputParameters,
SAMPLE_RATE,
wave_samplerate,
framesPerBuffer,
paNoFlag,
// paClipOff | paDitherOff,
@@ -410,7 +411,7 @@ static int wave_open_sound()
&pa_stream,
NULL, /* no input */
&myOutputParameters,
SAMPLE_RATE,
wave_samplerate,
framesPerBuffer,
paNoFlag,
// paClipOff | paDitherOff,
@@ -427,14 +428,14 @@ static int wave_open_sound()
&pa_stream,
NULL, /* no input */
&myOutputParameters,
SAMPLE_RATE,
wave_samplerate,
framesPerBuffer,
paNoFlag,
// paClipOff | paDitherOff,
pa_callback,
(void *)userdata);
// err = Pa_OpenDefaultStream(&pa_stream,0,2,paInt16,(double)SAMPLE_RATE,FRAMES_PER_BUFFER,pa_callback,(void *)userdata);
// err = Pa_OpenDefaultStream(&pa_stream,0,2,paInt16,(double)wave_samplerate,FRAMES_PER_BUFFER,pa_callback,(void *)userdata);
}
mInCallbackFinishedState = false;
#endif
@@ -526,7 +527,7 @@ static void select_device(const char* the_api)
defaultAlsaIndex = hostInfo->defaultOutputDevice;
const PaDeviceInfo *deviceInfo = Pa_GetDeviceInfo( defaultAlsaIndex );
update_output_parameters(defaultAlsaIndex, deviceInfo);
if (Pa_IsFormatSupported(NULL, &myOutputParameters, SAMPLE_RATE) == 0)
if (Pa_IsFormatSupported(NULL, &myOutputParameters, wave_samplerate) == 0)
{
SHOW( "select_device > ALSA (default), name=%s (#%d)\n", deviceInfo->name, defaultAlsaIndex);
selectedIndex = defaultAlsaIndex;
@@ -541,7 +542,7 @@ static void select_device(const char* the_api)
update_output_parameters(i, deviceInfo);
if (Pa_IsFormatSupported(NULL, &myOutputParameters, SAMPLE_RATE) == 0)
if (Pa_IsFormatSupported(NULL, &myOutputParameters, wave_samplerate) == 0)
{
SHOW( "select_device > ALSA, name=%s (#%d)\n", deviceInfo->name, i);
@@ -613,12 +614,13 @@ void wave_set_callback_is_output_enabled(t_wave_callback* cb)
//<wave_init
// TBD: the arg could be "alsa", "oss",...
void wave_init()
void wave_init(int srate)
{
ENTER("wave_init");
PaError err;
pa_stream = NULL;
wave_samplerate = srate;
mInCallbackFinishedState = false;
init_buffer();
@@ -1023,7 +1025,7 @@ int wave_get_remaining_time(uint32_t sample, uint32_t* time)
{
// TBD: take in account time suplied by portaudio V18 API
a_time = sample - myReadPosition;
a_time = 0.5 + (a_time * 1000.0) / SAMPLE_RATE;
a_time = 0.5 + (a_time * 1000.0) / wave_samplerate;
}
else
{
@@ -1050,7 +1052,7 @@ void *wave_test_get_write_buffer()
// notdef USE_PORTAUDIO
void wave_init() {}
void wave_init(int srate) {}
void* wave_open(const char* the_api) {return (void *)1;}
size_t wave_write(void* theHandler, char* theMono16BitsWaveBuffer, size_t theSize) {return theSize;}
int wave_close(void* theHandler) {return 0;}
+1 -1
View File
@@ -7,7 +7,7 @@
extern int option_device_number;
extern void wave_init();
extern void wave_init(int samplerate);
// TBD: the arg could be "alsa", "oss",...
extern void* wave_open(const char* the_api);
+5 -4
View File
@@ -65,7 +65,6 @@ enum {
static t_wave_callback* my_callback_is_output_enabled=NULL;
#define SAMPLE_RATE 22050
#define ESPEAK_FORMAT PA_SAMPLE_S16LE
#define ESPEAK_CHANNEL 1
@@ -90,6 +89,7 @@ static int time_offset_msec = 0;
static int just_flushed = 0;
static int connected = 0;
static int wave_samplerate;
#define CHECK_DEAD_GOTO(label, warn) do { \
if (!mainloop || \
@@ -475,7 +475,7 @@ static int pulse_open()
pthread_mutex_init( &pulse_mutex, (const pthread_mutexattr_t *)NULL);
ss.format = ESPEAK_FORMAT;
ss.rate = SAMPLE_RATE;
ss.rate = wave_samplerate;
ss.channels = ESPEAK_CHANNEL;
if (!pa_sample_spec_valid(&ss))
@@ -677,11 +677,12 @@ void wave_set_callback_is_output_enabled(t_wave_callback* cb)
//>
//<wave_init
void wave_init()
void wave_init(int srate)
{
ENTER("wave_init");
stream = NULL;
wave_samplerate = srate;
pulse_open();
}
@@ -846,7 +847,7 @@ int wave_get_remaining_time(uint32_t sample, uint32_t* time)
{
// TBD: take in account time suplied by portaudio V18 API
a_time = sample - a_timing_info.read_index;
a_time = 0.5 + (a_time * 1000.0) / SAMPLE_RATE;
a_time = 0.5 + (a_time * 1000.0) / wave_samplerate;
}
else
{
+5 -3
View File
@@ -77,12 +77,14 @@ static uint32_t last_play_position=0;
//
//<wave_init
void wave_init() {
void wave_init(int srate) {
ENTER("wave_init");
audio_info_t ainfo;
char *audio_device = NULL;
wave_samplerate = srate;
audio_device = getenv("AUDIODEV");
if (audio_device != NULL) {
if ((sun_audio_fd = open(audio_device, O_WRONLY)) < 0) {
@@ -108,7 +110,7 @@ void wave_init() {
SHOW("wave_init() play buffer size: %d\n", ainfo.play.buffer_size);
ainfo.play.encoding = AUDIO_ENCODING_LINEAR;
ainfo.play.channels = 1;
ainfo.play.sample_rate = SAMPLE_RATE;
ainfo.play.sample_rate = wave_samplerate;
ainfo.play.precision = SAMPLE_SIZE;
if (ioctl(sun_audio_fd, AUDIO_SETINFO, &ainfo) == -1) {
@@ -520,7 +522,7 @@ int wave_get_remaining_time(uint32_t sample, uint32_t* time)
(actual_index <= ainfo.play.samples)) {
*time = 0;
} else {
a_time = ((actual_index - ainfo.play.samples) * 1000) / SAMPLE_RATE;
a_time = ((actual_index - ainfo.play.samples) * 1000) / wave_samplerate;
*time = (uint32_t) a_time;
}
SHOW("wave_get_remaining_time for %d: %d\n", sample, *time);
+8 -5
View File
@@ -288,6 +288,8 @@ void WcmdqStop()
#ifdef USE_PORTAUDIO
Pa_AbortStream(pa_stream);
#endif
if(mbrola_name[0] != 0)
MbrolaReset();
}
@@ -1563,6 +1565,8 @@ void WavegenSetVoice(voice_t *v)
option_harmonic1 = 6;
}
WavegenSetEcho();
MarkerEvent(espeakEVENT_SAMPLERATE,0,wvoice->samplerate,out_ptr);
// WVoiceChanged(wvoice);
}
@@ -1797,11 +1801,6 @@ int WavegenFill(int fill_zeros)
static int resume=0;
static int echo_complete=0;
#ifdef TEST_MBROLA
if(mbrola_name[0] != 0)
return(MbrolaFill(fill_zeros));
#endif
while(out_ptr < out_end)
{
if(WcmdqUsed() <= 0)
@@ -1904,6 +1903,10 @@ int WavegenFill(int fill_zeros)
case WCMD_EMBEDDED:
SetEmbedded(q[1],q[2]);
break;
case WCMD_MBROLA_DATA:
result = MbrolaFill(length, resume);
break;
}
if(result==0)