OSDN Git Service

updated JTalk. split word sequence before synthesis
authorTakuya Nishimoto <nishimotz@gmail.com>
Sun, 10 Nov 2013 15:49:38 +0000 (00:49 +0900)
committerTakuya Nishimoto <nishimotz@gmail.com>
Sun, 10 Nov 2013 15:49:38 +0000 (00:49 +0900)
jptools/jtalkRunner.py
source/synthDrivers/jtalk/_jtalk_core.py
source/synthDrivers/jtalk/_nvdajp_jtalk.py
source/synthDrivers/jtalk/mecab.py

index a6bf1c9..237d942 100644 (file)
@@ -57,22 +57,31 @@ def do_synthesis(msg, voice_args, do_play):
        Mecab_analysis(s, mf)
        Mecab_print(mf, __print, CODE_='utf-8')
        Mecab_correctFeatures(mf, CODE_='utf-8')
-       Mecab_utf8_to_cp932(mf)
-       Mecab_print(mf, __print, CODE_='cp932')
        fperiod = voice_args['fperiod']
-       data = libjt_synthesis(mf.feature,
-                                                  mf.size,
-                                                  fperiod_ = fperiod,
-                                                  logwrite_ = __print)
-       mf = None
-       if data and do_play:
-               pa_play(data, samp_rate = voice_args['samp_rate'])
-               w = wave.Wave_write("_test.wav")
-               w.setparams( (1, 2, voice_args['samp_rate'], len(data)/2,
-                                         'NONE', 'not compressed') )
-               w.writeframes(data)
-               w.close()
-       libjt_clear()
+       data_array = []
+       ar = Mecab_splitFeatures(mf, CODE_='utf-8')
+       __print('array size %d' % len(ar))
+       for a in ar:
+               __print('feature size %d' % a.size)
+               Mecab_print(a, __print, CODE_='utf-8')
+               Mecab_utf8_to_cp932(a)
+               data = libjt_synthesis(a.feature,
+                                                          a.size,
+                                                          fperiod_ = fperiod,
+                                                          logwrite_ = __print)
+               __print('data size %d' % len(data))
+               data_array.append(data)
+               libjt_refresh()
+               del a
+       del mf
+       for data in data_array:
+               if data and do_play:
+                       pa_play(data, samp_rate = voice_args['samp_rate'])
+                       w = wave.Wave_write("_test.wav")
+                       w.setparams( (1, 2, voice_args['samp_rate'], len(data)/2,
+                                                 'NONE', 'not compressed') )
+                       w.writeframes(data)
+                       w.close()
 
 def main(do_play = True):
        njd = NJD()
@@ -96,8 +105,8 @@ def main(do_play = True):
        _nvdajp_predic.setup()
 
        msgs = [
-               '100.25ã\83\89ã\83«ã\80\82ã\82¦ã\82§ã\83«ã\82«ã\83 ã\83\88ã\82¥ã\83¼ nvda ã\83\86ã\83³ã\82­ã\83¼ã\81®insertã\82­ã\83¼ã\81¨ã\83¡ã\82¤ã\83³ã\81®insertã\82­ã\83¼ã\81®ä¸¡æ\96¹ã\81\8cnvdaキーとして動作します',
-               'YouTube iTunes Store sjis co jp',
+               '100.25ã\83\89ã\83«ã\80\82ã\82¦ã\82§ã\83«ã\82«ã\83 ã\83\88ã\82¥ã\83¼ nvda ã\83\86ã\83³ã\82­ã\83¼ã\81®insertã\82­ã\83¼ã\81¨ã\80\81ã\83¡ã\82¤ã\83³ã\81®insertã\82­ã\83¼ã\81®ä¸¡æ\96¹ã\81\8cã\80\81nvdaキーとして動作します',
+               'You Tube i Tunes Store sjis co jp',
                '十五絡脈病証。', # nvdajp ticket 29828
                'マーク。まーく。', # nvdajp ticket 29859
                '∫⣿♪ ウェルカムトゥー 鈹噯呃瘂蹻脘鑱涿癃 十五絡脈病証 マーク。まーく。ふぅー。ふぅぅぅぅぅー。ぅー。ぅぅー。',
index 83e7aa1..b4f3927 100644 (file)
@@ -446,28 +446,28 @@ def libjt_synthesis(feature, size, fperiod_=80, feed_func_=None, is_speaking_fun
                libjt.njd_set_pronunciation(njd)
                libjt.njd_set_digit(njd)
                libjt.njd_set_accent_phrase(njd)
-       except WindowsError(e):
+       except WindowsError as e:
                if logwrite_ : logwrite_('libjt_synthesis error #1 ' + str(e))
        # exception: access violation reading 0x00000000
        # https://github.com/nishimotz/libopenjtalk/commit/10d3abda6835e0547846fb5e12a36c1425561aaa#diff-66
        try:
                libjt.njd_set_accent_type(njd)
-       except WindowsError:
-               if logwrite_ : logwrite_('libjt_synthesis njd_set_accent_type() error ')
+       except WindowsError as e:
+               if logwrite_ : logwrite_('libjt_synthesis njd_set_accent_type() error ' + str(e))
        try:
                libjt.njd_set_unvoiced_vowel(njd)
                libjt.njd_set_long_vowel(njd)
                libjt.njd2jpcommon(jpcommon, njd)
                libjt.JPCommon_make_label(jpcommon)
-       except WindowsError(e):
+       except WindowsError as e:
                if logwrite_ : logwrite_('libjt_synthesis error #2 ' + str(e))
        if is_speaking_func_ and not is_speaking_func_() :
                libjt_refresh()
                return None
        try:
                s = libjt.JPCommon_get_label_size(jpcommon)
-       except WindowsError:
-               if logwrite_ : logwrite_('libjt_synthesis JPCommon_get_label_size() error ')
+       except WindowsError as e:
+               if logwrite_ : logwrite_('libjt_synthesis JPCommon_get_label_size() error ' + str(e))
        buf = None
        if s > 2:
                try:
@@ -476,8 +476,8 @@ def libjt_synthesis(feature, size, fperiod_=80, feed_func_=None, is_speaking_fun
                        libjt.HTS_Engine_create_sstream(engine)
                        libjt.HTS_Engine_create_pstream(engine)
                        libjt.HTS_Engine_create_gstream(engine)
-               except WindowsError:
-                       if logwrite_ : logwrite_('libjt_synthesis error #3 ')
+               except WindowsError as e:
+                       if logwrite_ : logwrite_('libjt_synthesis error #3 ' + str(e))
                if is_speaking_func_ and not is_speaking_func_() :
                        libjt_refresh()
                        return None
@@ -489,7 +489,7 @@ def libjt_synthesis(feature, size, fperiod_=80, feed_func_=None, is_speaking_fun
                        buf = string_at(speech_ptr, byte_count)
                        if feed_func_: feed_func_(buf)
                        #libjt.jt_save_logs("_logfile", engine, njd)
-               except WindowsError:
-                       if logwrite_ : logwrite_('libjt_synthesis error #5 ')
+               except WindowsError as e:
+                       if logwrite_ : logwrite_('libjt_synthesis error #5 ' + str(e))
        if logwrite_ : logwrite_('libjt_synthesis done.')
        return buf
index 107ed6f..2593a47 100644 (file)
@@ -135,23 +135,28 @@ def _jtalk_speak(msg, index=None, prop=None):
                        if DEBUG: _jtalk_core.Mecab_print(mf, logwrite)
                        _jtalk_core.Mecab_correctFeatures(mf)
                        if DEBUG: _jtalk_core.Mecab_print(mf, logwrite)
-                       _jtalk_core.Mecab_utf8_to_cp932(mf)
-                       if DEBUG: _jtalk_core.Mecab_print(mf, logwrite, CODE_='cp932')
-                       if DEBUG: logwrite("Mecab_analysis done")
-                       if not isSpeaking(): _jtalk_core.libjt_refresh(); return
-                       _jtalk_core.libjt_synthesis(mf.feature, mf.size, 
-                               fperiod_ = fperiod_current, 
-                               feed_func_ = player.feed, # player.feed() is called inside
-                               is_speaking_func_ = isSpeaking, 
-                               thres_ = thres_level,
-                               thres2_ = thres2_level,
-                               level_ = int(max_level * speaker_attenuation),
-                               logwrite_ = lw,
-                               lf0_offset_ = lo,
-                               lf0_amp_ = la)
-                       mf = None
-                       if DEBUG: logwrite("libjt_synthesis done")
-                       _jtalk_core.libjt_refresh()
+                       ar = _jtalk_core.Mecab_splitFeatures(mf, CODE_='utf-8')
+                       for m in ar:
+                               _jtalk_core.Mecab_utf8_to_cp932(m)
+                               if DEBUG: _jtalk_core.Mecab_print(m, logwrite, CODE_='cp932')
+                               if DEBUG: logwrite("Mecab_analysis done")
+                               if not isSpeaking(): _jtalk_core.libjt_refresh(); return
+                               _jtalk_core.libjt_synthesis(
+                                       m.feature,
+                                       m.size,
+                                       fperiod_ = fperiod_current,
+                                       feed_func_ = player.feed, # player.feed() is called inside
+                                       is_speaking_func_ = isSpeaking,
+                                       thres_ = thres_level,
+                                       thres2_ = thres2_level,
+                                       level_ = int(max_level * speaker_attenuation),
+                                       logwrite_ = lw,
+                                       lf0_offset_ = lo,
+                                       lf0_amp_ = la)
+                               del m
+                               if DEBUG: logwrite("libjt_synthesis done")
+                               _jtalk_core.libjt_refresh()
+                       del mf
                except WindowsError:
                        if DEBUG: logwrite("WindowsError")
        player.sync()
index cf5b8da..9aa4631 100644 (file)
@@ -427,3 +427,29 @@ def Mecab_utf8_to_cp932(mf):
        for pos in xrange(0, mf.size):\r
                s = Mecab_getFeature(mf, pos, CODE_ = 'utf-8')\r
                Mecab_setFeature(mf, pos, s, CODE_ = 'cp932')\r
+\r
+def Mecab_duplicateFeatures(mf, startPos = 0, stopPos = None, CODE_ = 'utf-8'):\r
+       if not stopPos:\r
+               stopPos = mf.size\r
+       nbmf = NonblockingMecabFeatures()\r
+       newPos = 0\r
+       for pos in xrange(startPos, stopPos):\r
+               s = Mecab_getFeature(mf, pos, CODE_)\r
+               Mecab_setFeature(nbmf, newPos, s, CODE_)\r
+               newPos += 1\r
+       nbmf.size = newPos\r
+       return nbmf\r
+\r
+def Mecab_splitFeatures(mf, CODE_ = 'utf-8'):\r
+       ar = []\r
+       startPos = 0\r
+       for pos in xrange(mf.size):\r
+               a = Mecab_getFeature(mf, pos, CODE_).split(',')\r
+               if a[1] == u'記号' and a[2] in (u'空白', u'句点', u'読点'):\r
+                       f = Mecab_duplicateFeatures(mf, startPos, pos + 1, CODE_)\r
+                       ar.append(f)\r
+                       startPos = pos + 1\r
+       if startPos < mf.size:\r
+               f = Mecab_duplicateFeatures(mf, startPos, mf.size, CODE_)\r
+               ar.append(f)\r
+       return ar\r