MMDの物理演算エンジン搭載テストの紹介

 ZHUOさんが紹介されている「ものすごい"test"動画」をご紹介します。確かにこれはすごい。

 技術的には、MMDに物理演算エンジンを搭載し、髪の毛やスカートの揺れを自動化したものと推定します。

 背景も何も無く、カメラ切り替えすらない単なるデモなのに、見ているだけでワクワクしますね。これで今までのMMD動画を作り直したらどんな風に見えるのか、そして全て物理現象(髪やスカートの揺れ)を手でMMDで打ち込んでいた職人たちが、その物理現象の打ち込みという頚木から開放されたならば、どんな作品を量産し始めるのか。

 MMD作者の樋口優さんに、この場を借りて感謝いたします。MMDの将来が楽しみです。

| | コメント (3) | トラックバック (0)

VocaSim

ITMediaの記事で、MikuMikuVoice と並んで VocaSim が取り上げられています。
VOCALOID“神調教”技術「ぼかりす」実用化へ、ヤマハと産総研が連携

一方、ユーザーのあいだから、ぼかりすと同様の成果を出すことができるソフトウェアがいくつも出され、「MikuMikuVoice」「VocaSim」などではすでに多くの作品が公開されている。

VocaSimはコマンドラインツールであり、樋口優さんのMikuMikuVoiceと比べればクセがあって使いにくい筈ですので、なか なかユーザが増えないですね。(VocaSimに使いやすいGUIを被せるなりのバージョンアップしろという話もありますが(笑)

教えて!goo に 「VocaSim」の使い方の質問があり、処理したいVSQファイルと同じフォルダに実行ファイルを置くという方法が紹介されています。とりあえず暫定ですが、ユーザの方々にはこの方法で処理いただければと思います。

| | コメント (2) | トラックバック (0)

VSQのファイル仕様(推定)

このところ多忙のため、更新の間が空いてしまいました。
さて、かの有名な「初音ミク」のアプリケーションが出力するファイルを、その拡張子から「VSQファイル」と呼ぶのですが、(すいません、初見の方への説明です)このVSQファイルはヤマハのVOCALOID2独自形式であり、現時点でフォーマットは公式には公表されていません。

VOCALOID本の中で特集して欲しいんですけどね・・・(とマスコミの方にヒントを流す)

このVSQファイル仕様を推定するwikiが出来たようです。なかなかハードな良い出来ですので、今後のフリーソフト作成の参考に致したくおもいます。

VSQのファイル仕様(推定)
http://www9.atwiki.jp/boare/pages/16.html

| | コメント (2) | トラックバック (0)

MIKU_TALK 修復

 日本語の文章を初音ミクの喋りファイル (.vsq) に変換する MIKU_TALK WEBアプリケーションがこのところ停止しており、申し訳ありませんでした。復旧いたしましたのでお試しください。

和泉聡のソフトウエア実験室
http://akira-izumi.hp.infoseek.co.jp/

停止していた原因は、Yahoo!形態素解析WEBサービスのURLが変更になった為です。変更の旨はYahooグループに掲載されていますね。

Date:  2008年8月12日(火) 午後0時00分
Subject:  Yahoo!デベロッパーネットワークからの重要なお知らせ

Yahoo!デベロッパーネットワークをご利用いただき
誠にありがとうございます。

Yahoo!デベロッパーネットワーク運営スタッフより、
重要なお知らせを申しあげげます。

この度、当社が提供するWebサービスのURLを、yahoo.co.jpドメインから、
yahooapis.jpドメインに移行することになりました。

この移行に伴い、本日よりYahoo!デベロッパーネットワークの
Webページ上に記載されているすべてのWebサービスのURLを
yahooapis.jpドメインに変更いたしました。

今後数か月間は、移行期間としてyahoo.co.jpドメインのWebサービス
へのアクセスも併行して可能になりますが、移行期間終了後は
yahooapis.jpドメインだけが有効になり、yahoo.co.jpドメインの
WebAPIはアクセスできなくなりますのでご注意ください。
お客様にはご迷惑をおかけしますが、今後は、アクセスするWebAPIの
URLを下記のとおり、yahooapis.jpドメインにご変更いただけますよう
よろしくお願いいたします。

また、今回の変更に伴い、yahoo.co.jpドメインのWebAPIに対して、
Flashからのアクセスに制限が設けられたWebAPIがあります
。(*1)
影響のあったお客様は、至急yahooapis.jpドメインでのアクセスに
ご変更いただけますようお願いいたします。

尚、移行期間の終了期日につきましては、別途ご連絡させていただきます。

大変お手数をお掛けいたしますが、なにとぞ、ご理解・ご協力のほど、
よろしくお願い申し上げます。

            記

■ ドメイン変更内容
アクセスするWebサービスのドメインを「yahoo.co.jp」から
「yahooapis.jp」に変更してください。

・変更前:api.search.yahoo.co.jp/・・・
  → 変更後:search.yahooapis.jp/・・・
・変更前:api.dir.yahoo.co.jp/・・・
  → 変更後:dir.yahooapis.jp/・・・
・変更前:api.auctions.yahoo.co.jp/・・・
  → 変更後:auctions.yahooapis.jp/・・・
・変更前:api.station.music.yahoo.co.jp/・・・
  → 変更後:station.music.yahooapis.jp/・・・
・変更前:api.map.yahoo.co.jp/MapsService/Flash/V1/・・・
  → 変更後:map.yahooapis.jp/MapsService/Flash/V1/・・・
・変更前:api.jlp.yahoo.co.jp/・・・
  → 変更後:jlp.yahooapis.jp/・・・ (*2)

・変更前:api.kaden.yahoo.co.jp/・・・
  → 変更後:kaden.yahooapis.jp/・・・
・変更前:api.news.yahoo.co.jp/・・・
  → 変更後:news.yahooapis.jp/・・・
・変更前:api.cert.yahoo.co.jp/・・・
  → 変更後:cert.yahooapis.jp/・・・

 *1 の下線部が原因で、MIKU_TALK が動作しなくなりました。MIKU_TALK はFLASH経由でYahoo!形態素解析を呼び出して、日本語の文章を平仮名・カタカナに変換しているからです。*2 の下線部は、Yahoo!形態素解析のURLです。
 これほど重要な情報なのですから、Yahoo!の担当の方は、アプリケーションIDを登録したユーザーに告知メールを送っていただきたかったです。何故動作しなくなったのだろうと、かなり悩みました。クロスドメイン呼出しを弾くようになったのだろうか、もしくは何らかの規約違反と見做されてWEB-API を拒絶されるようになったのだろうか等と考えたりもしました。
 原因さえ判れば修復は簡単で、単に形態素解析の呼出URLを変更するだけで、FTPアップロードを含めて数分の作業でした。

| | コメント (0) | トラックバック (0)

商標登録第5157451号

今年8月8日に、無事に商標「初音ミク」が登録されました。ちょっと驚いたのは栗原潔さんが代理人だったことです。栗原さんというと株式会社テックバイザージェイピーの取締役で、弁理士で、かつ初音ミクの合法的音楽配信サイトを作成されていることで有名な方ですね。商標登録出願の担当をされているとは知りませんでした。

(190)【発行国】日本国特許庁(JP)
(450)【発行日】平成20年9月9日(2008.9.9)
【公報種別】商標公報
(111)【登録番号】商標登録第5157451号(T5157451)
(151)【登録日】平成20年8月8日(2008.8.8)
(541)【登録商標(標準文字)】初音ミク
(500)【商品及び役務の区分の数】4
(511)【商品及び役務の区分並びに指定商品又は指定役務】
 第9類 移動体電話による通信を用いてダウンロードされる移動体電話機の着信用の音楽,録画済みビデオディスク及びビデオテープ,家庭用テレビゲームおもちゃ,携帯用液晶画面ゲームおもちゃ用のプログラムを記憶させた電子回路及びCD-ROM,電子楽器用自動伴奏プログラムを記憶させた電子回路及びCD-ROM,電子出版物
 第28類 おもちゃ,人形
 第41類 電子計算機端末による通信を用いて行うゲーム又はゲームに関する映像の提供,映画・演芸・演劇又は音楽の演奏の興行の企画又は運営,映画の上映・制作又は配給,音楽の演奏,移動体電話による通信を用いて行うゲームの提供
 第42類 インターネット・電子メールその他の通信ネットワークを用いた電子計算機用プログラムの提供,移動体電話による電子計算機用プログラムの提供,電子計算機用プログラムの提供
【国際分類第9版】
(210)【出願番号】商願2007-99911(T2007-99911)
(220)【出願日】平成19年9月6日(2007.9.6)
(732)【商標権者】
【識別番号】500434897
【氏名又は名称】クリプトン・フューチャー・メディア株式会社
【住所又は居所】北海道札幌市中央区南2条西12丁目 エクセルシアビル5F
(740)【代理人】
【識別番号】100139778
【弁理士】
【氏名又は名称】栗原 潔
【法区分】平成18年改正
【審査官】黒磯 裕子
(561)【称呼(参考情報)】ハツネミク
【検索用文字商標(参考情報)】初音ミク
【類似群コード(参考情報)】
 第9類 24A01、24E01、26A01、26D01
 第28類 24A01
 第41類 41E01、41E02、41E03、41K01、41Z99
 第42類 42X11

指定商品又は指定役務は出願時と比べ、ずいぶん減縮されました。以下の公開商標公報の指定商品又は指定役務のうち、登録された部分に下線を引きました。

(190)【発行国】日本国特許庁(JP)
(441)【公開日】平成19年10月18日(2007.10.18)
【公報種別】公開商標公報
(210)【出願番号】商願2007-99911(T2007-99911)
(220)【出願日】平成19年9月6日(2007.9.6)
(540)【商標】初音ミク
【標準文字】
(511)【商品及び役務の区分並びに指定商品又は指定役務】
 第9類 移動体電話による通信を用いてダウンロードされる移動体電話機の着信用の音楽録画済みビデオディスク及びビデオテープ,自動販売機,駐車場用硬貨作動式ゲート,作業記録機,写真複写機,手動計算機,製図用又は図案用の機械器具,タイムスタンプ,タイムレコーダー,電気計算機,パンチカードシステム機械,票数計算機,ビリングマシン,郵便切手のはり付けチェック装置,ウエイトベルト,レギュレーター,家庭用テレビゲームおもちゃ,電気溶接装置,メトロノーム,携帯用液晶画面ゲームおもちゃ用のプログラムを記憶させた電子回路及びCD―ROM電子楽器用自動伴奏プログラムを記憶させた電子回路及びCD―ROM電子出版物
 第28類 スキーワックス,遊園地用機械器具(業務用テレビゲーム機を除く。),愛玩動物用おもちゃ,おもちゃ人形,遊戯用器具,ビリヤード用具,運動用具,釣り具,昆虫採集用具
 第41類 ゲーム機械器具を備えた遊戯場・遊園地・その他の娯楽施設の提供,映画・演芸・演劇・音楽又は教育研修のための施設の提供,電子計算機端末による通信を用いて行うゲーム又はゲームに関する映像の提供,ボウリング場・その他の運動施設の提供,レコード又は録音済み磁気テープの貸与,録画済み磁気テープの貸与,おもちゃの貸与,遊園地用機械器具の貸与,スロットマシンの貸与,遊戯用器具の貸与,映画・演芸・演劇又は音楽の演奏の興行の企画又は運営,映画の上映・制作又は配給,演芸の上演,演劇の演出又は上演,音楽の演奏,放送番組の制作,音響用又は映像用のスタジオの提供,映写機及びその附属品の貸与,映写フィルムの貸与,移動体電話による通信を用いて行うゲームの提供
 第42類 インターネット・電子メールその他の通信ネットワークを用いた電子計算機用プログラムの提供移動体電話による電子計算機用プログラムの提供,気象情報の提供,建築物の設計,測量,地質の調査,機械・装置若しくは器具(これらの部品を含む。)又はこれらの機械等により構成される設備の設計,デザインの考案,電子計算機のプログラムの設計・作成又は保守,電子計算機・自動車その他その用途に応じて的確な操作をするためには高度の専門的な知識・技術又は経験を必要とする機械の性能・操作方法等に関する紹介及び説明,医薬品・化粧品又は食品の試験・検査又は研究,建築又は都市計画に関する研究,公害の防止に関する試験又は研究,電気に関する試験又は研究,土木に関する試験又は研究,農業・畜産又は水産に関する試験・検査又は研究,機械器具に関する試験又は研究,著作権の利用に関する契約の代理又は媒介,社会保険に関する手続きの代理,計測器の貸与,電子計算機の貸与,電子計算機用プログラムの提供,理化学機械器具の貸与,製図用具の貸与
(731)【出願人】
【氏名又は名称】クリプトン・フューチャー・メディア株式会社
【住所又は居所】札幌市中央区南2条西12丁目 エクセルシアビル5F

 この指定商品又は指定役務を見ると、クリプトン・フューチャー・メディア(株)の将来の事業の方向がなんとなく見えます。
 現在の商品である電子計算機用プログラムを基礎として、おもちゃ業界やゲーム業界に打って出て(これは今でもやっていますね)、そして、ONLINE VOCALOID に備えてネットワークサービスも考えているようです。

| | コメント (3) | トラックバック (0)

星のカケラ

一昨日に初音ミク「星のカケラ」を聴きました。偶然にも、昨年度に「初音ミク」を知ったときからほぼ1年が経過した時点です。この曲を聴くと、昨年度の弁理士試験の論文式筆記試験に合格し、嬉しいながらも口述試験に受かるかどうかと不安な思いを抱えながらも勉強を開始していた頃を思い出しました。音楽は、それを聴いていた頃の想いや感情と共に心に記憶されるように思います。

初音ミクの「星のカケラ」は、公式プロフィールページのデモソング01です。

以下は、咲音メイコの「星のカケラ」のカバーです。

さて、YAMAHAのVOCALOIDといえば、NetVOCALOIDがCEATECで発表されるようです。

CEATEC JAPAN デジタルネットワークステージ YAMAHA

出展製品-2

NetVOCALOID

製品分類:
その他関連製品・サービス

歌唱合成エンジン VOCALOID をサーバー上に実装し、Web API を通じてクライアントアプリケーション上で動作させるデモンストレーション。※この技術は Y2 プロジェクトを通して今後社外パートナーに提供されます。

 WEB-API 化は単なる手段に過ぎないので、これを元に更なる機能アップをお願いしたいと思います。例えばGUIの多国語対応が簡単にできるとか、多くのプラットフォームに簡単に対応できるとか、発音要素の追加が簡単にできるとかですね。

 多くのプラットフォームの対応というと、具体的にはNintendoDS や PlayStationPortable や iPhone から初音ミクの曲を作成することも可能ということになり、サービス提供範囲がかなり拡がるのと期待されます。

追記:2008年9月8日に開催された「CEATECとデジタルコンバージェンスの未来」 で、既に触れられていました。

「我々はボーカロイドの新しいエンジンを提供しますので、
そこ上で動く面白いサービスを考えてみませんか、一緒に面白いことをしませんかということです。
だから、Mac版どころじゃないんですね。じゃあ携帯電話でいいじゃないとか、DSとかPSPもありだとか・・」

| | コメント (0) | トラックバック (0)

星間飛行

おそらく、いちばん最初にvocasim 0.0.8 をお使いいただいた曲と思います。製作者は、kanadetailさんです。

 最近のマイブームが「星間飛行」だったので、ちょっと嬉しく思います。どうも有難うございました。

| | コメント (4) | トラックバック (0)

ダンシング☆サムライ

がくぼ独特の声音を使ったオリジナル曲です。vocasim を使っていただいておりますので備忘録として貼ります。ミク以外にも汎用的に使えることが判り、ちょっとほっとしております。今後のvocasim のバージョンアップの際も、初音ミク固有のチューニングは避けた方がいいかな。

| | コメント (4) | トラックバック (0)

ミクの学園ラブソング

vocasim 0.0.4 を使っていただいたnobitan さんのオリジナル曲を紹介します。あのスクリプトからこの作品を作り上げるまでは大変だったと思います。

nobitanさんには、ブログに vocasim の改良点の示唆もいただいておりますので、以下に検討いたします。

http://vocaloid.cocolog-nifty.com/blog/

課題1 音量調節ができない
ボーカロイドを人間らしく歌わせるには、何より抑揚をきっちりつける必要があります。特に音量のバラツキの多いリンレンでは、必要不可欠な作業です。しかしながら、vocasim は人間歌唱のシミュレートとして、音符の並びからフレーズを自動解析し、フレーズごとに盛り上がる箇所を決定しています。つまり、一つ一つの音符に対しては自動で音量が決まってしまい、ユーザーが演出することができません。じゃあ、vocasim 通した後で修正すれば?という考え方もありますが、ここで問題となるのはvocasimの微細振動データ。人間音声の不安定感を出すために、微妙なPIT やDYN変化が続くため、音量調整などをしてしまうと、この微細振動のデータが消えてしまうのです。

課題1の解決方法は、「事前に調教済みのデータの場合にはフレーズ自動解析を止めて、調教済みのDYN/PITを目標値としてPID制御する」ことです。これによりユーザが調教済みのデータを生かし、なおかつvocasim固有の微細振動を加えることが可能となります。

課題2 はっきりと発音しすぎてしまう
vocasimは、「ぼかりす」や「ぼかんないんです」の技術を参考に開発されており、特に音の立ち上がりのPIT変化やDYN変化に、通常の調教では考えられないほどの振幅を描きます。プレパレーションとかオーバーシュート、とかいう部分です。ところがこいつがクセモノで、全ての音符に一律に掛かってしまうため、ここはレガートにしたいなーという箇所全てが明瞭な発音となってしまいます。全体的にスタッカートな感じになってしまうのです。

この解決方法は、現在検討中です。なにか簡単な手段があるような気がします。

課題3 ある程度調教済みのデータを通すと悲惨なことに。
調教をしていると、音符を分割するケースが割と頻繁に発生します。あたりまえですがvocasimは、こうした音符分割のデータを普通に分かれていると判断し、それぞれに立ち上がりの極端なカーブを作ってしまうので、結果調教が進んでいるデータであればあるほど妙なことになってしまいます。

この解決方法は、音符分割のパターンを内部に記憶して、それらを1つの音符として扱うことです。例えば「ぼおかろいど」をそのまま vocasim に通すと「ぼ・お・か・ろ・い・ど」に分割して発音しますが、母音が共通する部分の「ぼお」は1つの音符として一連称呼した方が自然になるかと思います。

課題4 ビブラートの設定ができない。
基本的にvocasimのビブラートの掛かり具合は、フレーズ解析により決定されているようで、フレーズの一番後ろで延ばしている音に対して深くかかります。ところが、歌い手は常にそういった歌い方をしているわけではなく、むしろここはビブラートかけたくないなぁとか、そういった箇所もあるわけです。これらをどうやってコントロールするのか・・・という点も課題の一つでした。

この解決方法は「ビブラートなしのオプションを設けて、Vocaloid editor 側でビブラートを掛けることです。現在の vocasim 0.0.8 に搭載されていますのでご利用ください。

余談ですが、nobitanさんのブログのタイトルを見て、「目指せP」というプロデューサー名称が付与されるに違いないと思ったのは自分だけでしょうか。

| | コメント (2) | トラックバック (0)

がくぼがきた日

動画を見て大笑いしてしまったので、備忘録に貼ります。自分的には「特盛りの姫」ってところで吹きました。らぶデス改造MEIKOに「姉さん特盛です」のコメントが付いて以来、MEIKO=特盛のイメージなのでしょうね。

| | コメント (0) | トラックバック (0)

VocaSim 0.0.8

vocasim 0.0.8 を作成しました。「課題」は解決出来ておらず、主としてバグフィックスですがご容赦ください。

「vocasim008.zip」をダウンロード

主たる変更点は以下のものです。

・EXE形式のファイルとPerlスクリプトが入っていますので、Perl や MIDI-Perl のインストール無しに動作しますし、細かく Perl スクリプトをチューニングしていただくこともできます。
・BPMがデフォルトの120以外の場合にビブラート周波数が変動してしまう不具合を修正しました。

・ビブラートなし、ビブラート弱・中・強が選択可能となりました。

・トラック毎に乱数でビブラート周波数と位相が選択されるようになりました。これでコーラスに対応できるようになりました。

http://piapro.jp/content/ut3xxornucrad4hs

PiaPro にアップロードした試作品の「トロイカ」のコーラスです。

| | コメント (6) | トラックバック (0)

vocasimによる合唱のテスト #3

ステレオにして、1トラック目のミクから3トラック目のミクまで左から順番にならべてみました。

http://piapro.jp/content/ia77zsxhu09usc7c

まだロボットくささが抜けないですね。人間の合唱についてもう少し検討が必要なようです。

| | コメント (0) | トラックバック (0)

vocasim による合唱のテスト

いろいろなミク3人の合唱です。
ビブラート周波数と微細振動の周波数と音量と音高をトラックごとに乱数で生成して、トラック毎のハーモニーが聞こえないかと考えたものです。

http://piapro.jp/content/u7ov7ez31abxyxvj
 
でも、いまいち合唱っぽくないですね。まだミクそれぞれのキャラが立ってないんじゃないかと思います。他にもパラメータを変動させないとダメかな?

| | コメント (0) | トラックバック (0)

MIDI-Perl のインストール

ActivePerl のインストール方法は、kent-web に画面遷移が詳細に説明されています。説明されているバージョンは 5.6.1 ですが、現在のバージョンでもほぼ同様とおもいます。
http://www.kent-web.com/www/anhttpd/perl_inst.html

ActivePerl のインストールが終わったならば、MIDI-Perl のインストールです。MIDI-Perl はMIDIファイルを読み書きするためのモジュールです。

①インターネット接続環境において、Administrator アカウントでログインしてください。日本語のログイン名だとインストールできない場合があります。
②次に、スタートメニューの「すべてのプログラム」⇒「アクセサリ」から、「コマンドプロンプト」を起動してください。

③ppm-shell を起動して、 install MIDI-Perl とタイプしてください。以下の画面になったらインストール成功です。
Midiperl

この作業によって、C:\Perl\site\lib フォルダ下に、MIDI.pm ファイル及び MIDI フォルダが作られ、C:\Perl\site\lib\midi フォルダ下に Event.pm Opus.pm Score.pm Simple.pm Track.pm が作られます。

| | コメント (1) | トラックバック (0)

ActivePerlのダウンロード方法

Perl は初めてという方への ActivePerl のダウンロード方法のご紹介です。

①まず最初に ActiveState社のサイトにアクセスします。
http://www.activestate.com/index.mhtml

②一番下の「Alll Downloads」をクリックします。
Perl_dl_01

③ActivePerl の項目右にある「Get Current Release」をクリックします。
Perl_dl_02_2

④ActivePerl の Download を選択します。
Perl_dl_03

⑤名前やメールアドレス等の入力画面が表示されますが、これはオプションなのでそのまま Continue ボタンを押して問題ありません。

Perl_dl_04

⑥ActivePerl 5.8.8.822 から、オペレーティングシステムを選択してインストールします。通常は "Download ActivePerl 5.8.8.822 for Windows(x86)" の MSI で問題ありません。
Perl_dl_05
⑦ファイルのダウンロード画面が表示されたら、保存ボタンをクリックして適切なフォルダを選択します。
Perl06

| | コメント (0) | トラックバック (0)

VocaSim の比較動画とEXE化

Closebox and Openpod の松尾さんが「ベタ打ち」「VocaSim」「MikuMikuVoice」の比較動画を発表されました。改変も再配布も自由ですので、心ゆくまで触っていただければ幸いです。

Mashpod さんは、VocaSim をEXEファイルにしていただきました。恐らく ActivePerl のインストール無しに動作するとおもいます。どうも有難うございました。

http://mashpod.vox.com/library/post/vocasim004pl%E3%81%AEexe%E5%8C%96%E6%9A%AB%E5%AE%9A.html

| | コメント (3) | トラックバック (0)

vocasim 0.0.4 (source)

vocasim004.pl のソースコードです。

#!/perl -w
########################################################################
#
# Vocal Simulator Ver.0.0.4
# vocasim004.pl
#
# Programmed by A.Izumi 5/Jul/2008
#
use strict;
use MIDI;
use MIDI::Simple;

use constant {
    PHRASE_BEGIN  => 1,
    PHRASE_END    => 2,
};
use constant {
    INTERVAL_TIME    => 120,
    EPILOGUE_TIME    => 50,
};

my $fname = shift;
if( !defined($fname) ) {
  print ("使い方:vocasim004.pl in_vsq out_vsq mode\n");
  print ("mode = 元気よく,のんびりと \n");
  die;
}
my $o = MIDI::Opus->new({ "from_file" => $fname || die });
my @tracks = $o->tracks;

my $vsqname = shift;
if( !defined($vsqname) ) {
  $vsqname = "a_out.vsq";
}
my $trainingMode = shift;
if( !defined($vsqname) ) {
  $trainingMode = "元気よく";
}
my $vibratoCycle = 110;
my $deltawaveCycle = 47;
my $delay_time = 8;

#
# 「元気よく」がデフォルト
#
my $Kp = 0.03;
my $Ki = 0.0003;
if( $trainingMode eq "のんびりと" ) {
$Kp = 0.01;
$Ki = 0.0001;
}

#
# 各トラック毎の処理
#
my $ref_array_track = [0];
my $j;
for(my $i = 0; $i < scalar(@tracks); $i++) {
  my @thisEvents = ();
  my $text = "";
  # テキスト部分の抽出
  foreach my $events ($tracks[$i]->events) {
    if ($events->[0] eq "text_event"){
      $text .= $events->[2];
    }
  }
  # テキスト部分から DM:数字4桁を削除する。
  my @trackText =();
  my $my_miku_phonetics="";
  $text =~ s/DM:[0-9]{4}://go;

  my @eventListSection = ();
#
# いったんセクション毎に分解する
#
  my @sections = ();
  @sections = split(/\[/,$text);
  shift @sections;
  for(my $k = 0; $k < scalar(@sections); $k++) {
    $sections[$k] = "\[".$sections[$k];
  }

  for(my $k = 0; $k < scalar(@sections); $k++) {
    if( index($sections[$k],"\[EventList\]") == 0 ) {
      @eventListSection = split(/\n/,$sections[$k]);
    }
  }
  shift @eventListSection;
  pop @eventListSection;

  my @hId = ();
  my $idx_event = 0;
  foreach my $thisEvent (@eventListSection) {
    my $hash = {};
    my @event_elements = ();
    @event_elements = split(/=/,$thisEvent);
    $hash->{"Timing"} = $event_elements[0];
    $hash->{"id_section"} = $event_elements[1];
#
# イベントに対応した、IDセクションの抽出
#
    my $idSection = "";
    foreach my $thisSection0 (@sections) {
      if( index($thisSection0,$hash->{id_section} ) == 1 ) {
        $idSection = $thisSection0;
      }
    }
    if( $idSection eq "" ) {
      next;
    }
    my @id_elements = ();
    @id_elements = split(/\n/,$idSection);
    foreach my $thisElement (@id_elements) {
      my $equal = index($thisElement,"=");
      if( 0 < $equal ) {
        my @terms = split(/=/,$thisElement);
        $hash->{$terms[0]} = $terms[1];
      }
    }
#
# IDセクションに対応した、hセクションの抽出
#
    if( !defined($hash->{"LyricHandle"}) ) {
      next;
    }
    my $hSection = "";
    foreach my $thisSection1 (@sections) {
      if( index($thisSection1,$hash->{"LyricHandle"} ) == 1 ) {
        $hSection = $thisSection1;
      }
    }
    if( $hSection eq "" ) {
      next;
    }
    my @h_elements = ();
    @h_elements = split(/\n/,$hSection);
    foreach my $thisElement1 (@h_elements) {
      my $equal = index($thisElement1,"=");
      if( 0 < $equal ) {
        my @terms = split(/=/,$thisElement1);
        $hash->{$terms[0]} = $terms[1];
      }
    }
    push(@hId,$hash);
    $idx_event++;
  }
#
# フレーズ内の発音要素の判断
#
  my $timing_last = 0;
  for($j = 0; $j < scalar(@hId); $j++) {
    $hId[$j]->{"Interval"} = $hId[$j]->{"Timing"} - $timing_last;
    $hId[$j]->{"Location"} = 0;
    if( $j == 0 ) {
      $hId[$j]->{"Location"} = PHRASE_BEGIN;
    } else {
      if( INTERVAL_TIME < ($hId[$j]->{"Timing"} - $timing_last)) {
        $hId[$j-1]->{"Location"} |= PHRASE_END;
        $hId[$j]->{"Location"} = PHRASE_BEGIN;
      }
    }
    if($j == scalar(@hId)-1){
      $hId[$j]->{"Location"} = PHRASE_END;
    }
    $timing_last = $hId[$j]->{"Timing"} + $hId[$j]->{"Length"};
  }

  my $timing_phrase_begin = 0;
  for($j = 0; $j < scalar(@hId); $j++) {
    if( ($hId[$j]->{"Location"} & PHRASE_BEGIN) || $j==0 ) {
      $timing_phrase_begin = $hId[$j]->{"Timing"};
    }
    $hId[$j]->{"PhraseBegin"} = $timing_phrase_begin;
  }

  my $timing_phrase_end = 0;
  for($j = scalar(@hId)-1; $j >= 0; $j--) {
    if( ($hId[$j]->{"Location"} & PHRASE_END) || $j == scalar(@hId) - 1 ) {
      $timing_phrase_end = $hId[$j]->{"Timing"} + $hId[$j]->{"Length"};
    }
    $hId[$j]->{"PhraseEnd"} = $timing_phrase_end;
  }
  for($j = 0; $j < scalar(@hId); $j++) {
    printf("%s: %d : %d : %d :%d: %d:%d: %s\n",
        $hId[$j]->{"Timing"},
        $hId[$j]->{"Length"},
        $hId[$j]->{"Note#"},
        $hId[$j]->{"Interval"},
        $hId[$j]->{"Location"},
        $hId[$j]->{"PhraseBegin"},
        $hId[$j]->{"PhraseEnd"},
        $hId[$j]->{"L0"});
  }
  my $myDynamicsBPList  = "\[DynamicsBPList\]\n";
  my $myPitchBendBPList = "\[PitchBendBPList\]\n";
  my $myPitchBendSensBPList = "\[PitchBendSensBPList\]\n";

  my $currentDynamics  = 0.0;
  my $lastDynamics     = -1;
  my $proportionalDynamics = 0.0;
  my $integralDynamics = 0.0;
  my $targetDynamics   = 0.0;
  my $KpDynamics = 0;
  my $KiDynamics = 0;
  my $thisDynamics  = 0;

  my $currentPitchbend   = -1.0;
  my $lastPitchbend = -8192;
  my $proportionalPitchbend = 0.0;
  my $integralPitchbend  = 0.0;
  my $targetPitchbend = -1.0;
  my $KpPitchbend = 0;
  my $KiPitchbend = 0;
  my $thisPitchbend = 0;

  my $phraseVibrato   = 0.0;
  my $swingVibratoPit = 0.1;
  my $swingVibratoDyn = 0.02;

  for($j = 0; $j < scalar(@hId); $j++) {
    if( ($hId[$j]->{"Location"} & PHRASE_BEGIN) ) {
      $currentDynamics  = 0.0;
      $currentPitchbend = -1.0;
    }
    $integralDynamics = 0.0;
    $integralPitchbend  = 0.0;
    my @proportionalDynamicsAry = ();
    my @proportionalPitchbendAry = ();

    for(my $k=0; $k<$hId[$j]->{"Length"}; $k++) {
      my $thisTiming   = $hId[$j]->{"Timing"} + $k;
      my $thisPhraseDynamics =
        sin(3.141592*
          (($thisTiming - $hId[$j]->{"PhraseBegin"})
           /($hId[$j]->{"PhraseEnd"} - $hId[$j]->{"PhraseBegin"})*90+45)/180.0);
#
# PID制御の目標値の設定
#
      $targetDynamics  = 1.0;
      $targetPitchbend = 0.0;
      my $vibratoDynamics  = 0;
      my $vibratoPitchbend = 0;
#
# 外乱の算出
#
      $phraseVibrato = ($k*2.0*3.141592)/$vibratoCycle;
      if( ($hId[$j]->{"Location"} & PHRASE_END) ) {
        $swingVibratoPit = 0.008 + 0.016 * $phraseVibrato/(2.0*3.141592*2.0);
        if( 0.03 < $swingVibratoPit ) {
          $swingVibratoPit = 0.03;
        }
        $swingVibratoDyn = 0.004 + 0.001 * $phraseVibrato/(2.0*3.141592*2.0);
        if( 0.01 < $swingVibratoDyn ) {
          $swingVibratoDyn = 0.01;
        }
      } else {
        $swingVibratoPit = 0.004;
        $swingVibratoDyn = 0.002;
      }
      $vibratoDynamics  = $swingVibratoDyn*sin($phraseVibrato);
      $vibratoPitchbend = $swingVibratoPit*sin($phraseVibrato);

      my $phraseDeltawave = ($k*2.0*3.141592)/$deltawaveCycle;
      my $deltawavePitchbend = 0.008*sin($phraseDeltawave)/3.0;
      my $deltawaveDynamics  = 0.004*sin($phraseDeltawave)/3.0;

#
# 発音と発音の間の無音期間の設定と
# 比例積分制御のパラメータ設定
#
      my $noteDiff = abs($hId[$j]->{"Note#"} - 70);
      if( 5 < $noteDiff ) {
        $noteDiff = 5;
      }
      $KpDynamics  = $Kp *(1.0 + 0.2* $noteDiff);
      $KiDynamics  = $Ki *(1.0 + 0.2* $noteDiff);
      $KpPitchbend = $Kp *(1.0 + 0.2* $noteDiff);
      $KiPitchbend = $Ki *(1.0 + 0.2* $noteDiff);
      if( !($hId[$j]->{"Location"} & PHRASE_END) and  INTERVAL_TIME < $hId[$j]->{"Length"} and  $hId[$j]->{"Length"} - EPILOGUE_TIME < $k ) {
        if( $targetDynamics != 0.0 ) {
          $integralDynamics = 0.0;
          $integralPitchbend = 0.0;
          $phraseVibrato = 0.0;
        }
        $targetDynamics = 0.0;
        $targetPitchbend = -1.0;

        $KpDynamics  = $Kp*3.0;
        $KiDynamics  = $Ki*3.0;
        $KpPitchbend = $Kp*3.0;
        $KiPitchbend = $Ki*3.0;
      }
#
#    DYN のPID制御
#
      $proportionalDynamicsAry[$k] = $targetDynamics - $currentDynamics;
      if( $k < $delay_time ) {
        $proportionalDynamics = 0;
      } else {
        $proportionalDynamics = $proportionalDynamicsAry[$k - $delay_time];
      }
      $integralDynamics += $proportionalDynamics;
      $currentDynamics += $proportionalDynamics*$KpDynamics + $integralDynamics*$KiDynamics + $vibratoDynamics + $deltawaveDynamics;
      $thisDynamics  = int(($currentDynamics*50)*$thisPhraseDynamics+15);
      if( $thisDynamics < 0 ) {
        $thisDynamics = 0;
      } elsif( 127 <= $thisDynamics ) {
        $thisDynamics = 127;
      }
#
#    PIT のPID制御
#
      $proportionalPitchbendAry[$k] = $targetPitchbend - $currentPitchbend;
      if( $k < $delay_time ) {
        $proportionalPitchbend = 0;
      } else {
        $proportionalPitchbend = $proportionalPitchbendAry[$k - $delay_time];
      }
      $integralPitchbend += $proportionalPitchbend;
      $currentPitchbend += $proportionalPitchbend*$KpPitchbend + $integralPitchbend*$KiPitchbend + $vibratoPitchbend + $deltawavePitchbend;
      $thisPitchbend = int(($currentPitchbend)*(4096+2048));
      if( $thisPitchbend < -8191 ) {
        $thisPitchbend = -8191;
      } elsif( 8191 <= $thisPitchbend ) {
        $thisPitchbend =  8191;
      }

      if( $lastDynamics != $thisDynamics ) {
        $myDynamicsBPList  .= int($thisTiming). "=". $thisDynamics.  "\n";
      }
      $lastDynamics = $thisDynamics;
      if( $lastPitchbend != $thisPitchbend ) {
        $myPitchBendBPList .= int($thisTiming). "=". $thisPitchbend. "\n";
      }
      $lastPitchbend = $thisPitchbend;
      if( $myPitchBendSensBPList eq "\[PitchBendSensBPList\]\n" ) {
        $myPitchBendSensBPList .= int($thisTiming). "=1";
      }
    }
    if( ($hId[$j]->{"Location"} & PHRASE_END)) {
      $currentDynamics  = 0.0;
      $currentPitchbend = -1.0;
      $thisDynamics  = 20;
      $thisPitchbend = -4096 - 2048;
      my $thisTiming = $hId[$j]->{"Timing"} + $hId[$j]->{"Length"};
      $myDynamicsBPList  .= int($thisTiming). "=". $thisDynamics.  "\n";
      $myPitchBendBPList .= int($thisTiming). "=". $thisPitchbend. "\n";
    }
  }

  for(my $k = 0; $k < scalar(@sections); $k++) {
    if( index($sections[$k],"\[PitchBendBPList\]") == 0 ) {
    } elsif( index($sections[$k],"\[DynamicsBPList\]")  == 0 ) {
    } elsif( index($sections[$k],"\[PitchBendSensBPList\]")  == 0 ) {
    } else {
      $my_miku_phonetics .= $sections[$k];
    }
  }
  if( 0 < scalar(@sections) ) {
    $my_miku_phonetics .= $myPitchBendBPList;
    $my_miku_phonetics .= $myDynamicsBPList;
    $my_miku_phonetics .= $myPitchBendSensBPList;
#print "\n\n";
#print  $my_miku_phonetics;
  }

  # テキスト部分をtext_event に再構成する。
  foreach my $events ($tracks[$i]->events) {
    if ($events->[0] eq "track_name"){
      push @thisEvents,$events;
    }
  }
  for(my $j=0; $j*119<length($my_miku_phonetics); $j++) {
    push @thisEvents, ['text_event', 0,
      sprintf("DM:%04d:",$j).substr($my_miku_phonetics,$j*119,119) ];
  }
  if( $i==0 ) {
    foreach my $events ($tracks[$i]->events) {
      if( $events->[0] ne "track_name"
      &&  $events->[0] ne "text_event" ){
        push @thisEvents,$events;
      }
    }
  }
  push @thisEvents,["end_track",0];
  my $this_track = MIDI::Track->new({ 'events' => \@thisEvents });
  $ref_array_track->[$i] = $this_track;
}
#
# マスタートラックとVoice1トラックからVSQファイルを生成する。
#
  my $opus = MIDI::Opus->new(
    { 'format' => 1, 'ticks' => 480, 'tracks' => $ref_array_track } );
  $opus->write_to_file( $vsqname );
  exit(0);
1;
__END__

| | コメント (0) | トラックバック (0)

VocaSim.0.0.4

VocalSIMulator –ボーカル歌唱のシミュレーション手法の提案

1、目的:
 VocalSimulator(以下 VocaSim)は、ヤマハのVOCALOIDシリーズのVSQファイルを入力として、音量や音高を自動調整して滑舌処理・オーバーシュートやビブラート及び微細変動処理を加えたVSQファイルを出力するものです。

VocaSim004.pl の実行結果 「星の界」
http://piapro.jp/content/bgxqrywgfuhums4s

2、従来技術との比較
 従来のVocaloid2 Editorは全てマウスで描画しており、オーバーシュートなどの細かな調整には膨大な工数が必要でした。唯一ビブラートのみは自動化されています。
 VocaListerner, MikuMikuVoice のアプローチは、肉声から音量と音高を抽出して、VSQファイルに反映させるというものです。肉声のニュアンスを緻密に反映できる特徴を有します。
 VocaSim のアプローチは、ボーカルをフィードバック制御システムとしてモデル化し、制御理論で元にPC内でシミュレーションするというものです。元歌不要でボーカルに似せた調整を掛けること可能です。

3、使用方法
(1)動作チェック環境
OS:WindowsXP
Perl処理系:ActivePerl 5.8.8
使用モジュール:MIDI-Perl v0.81
(2)インストール方法
ActivePerl 5.8.x をインストールしたのち、コマンドラインからppm-shell を起動します。
C:\hogehoge> ppm-shell
次に MIDI-Perl をインストールしてください。
 ppm> install MIDI-Perl
これで準備は完了です。
 そして、「vocasim004.pl」を右クリックしてダウンロードし、処理したいVSQと同じフォルダに入れてください。

(3)使い方
コマンドプロンプトを起動して、以下入力してください。出力VSQ名を省略したならば a_out.vsqに出力されます。
 C:\hogehoge> vocasim004.pl test.入力vsq test出力.vsq
のんびりとした感じの調教したかったら、3番目引数に「のんびりと」と記載願います。
 C:\hogehoge> vocasim004.pl test.入力vsq test出力.vsq のんびりと

4、処理の概要
(1)フレーズ処理
 発音要素ごとの時間間隔が一定値未満($interval_time 未満)ならば、そこでフレーズが終了すると見做しました。
 滑舌を明瞭にあらわす為、発音時間長が一定値以上($interval_time 以上)かつフレーズの末尾以外ならば、発音時間の末尾($prologue_time)で音量と音高が初期値に戻るよう制御しました。
 フレーズを理解して歌っている様をあらわす為、フレーズの包絡線が山なりの音量となるように制御しました。
(2)発音要素の処理
 ボーカルのフィードバック制御システムを以下にモデル化し、音量と音高それぞれをシミュレートします。原則として音量と音高は相関関係を有するよう制御します。
Vocasim_system_diagram

 ボーカルの脳は、耳で測定して目標値と比較するまでに応答遅延(8mSEC程度)を経たのち、目標値との差分をPID制御し、声帯にフィードバック指示します。
 声帯は、脳からの指示をもとに音声を出力します。このとき9Hz近傍のビブラートや、20Hz近傍の微細振動が外乱として加わります。なお、ビブラートはボーカルが故意に発振の大きさを調整可能とします。
 PID制御の式は以下のもので、これに応答遅延時間Dが加わります。

 制御指示 = Κp・(目標値-測定値)+Κi・Σ(目標値-測定値)

 応答遅延時間Dはボーカル固有であり、定数と考えられますので、立ち上がり波形の制御は、Κp・Κiのパラメータにのみ依存します。
 巧いボーカルをシミュレートしたい場合には臨界制動になるように制御し、ちょっと音痴なボーカルをシミュレートしたい場合にはオーバーシュートさせて制御します。 元気よい歌い方はΚp・Κiともに大きく、おとなしい歌い方はΚp・Κiともに小さくしてください。(VocaSim004.pl は、ちょっとオーバーシュート気味です)
 なお、VocaSim004.plでは「得意とするキー」の70から外れたならば力が入りすぎてオーバーシュートするようコーディングし、発音要素間の音量の谷間のときは、Κp・Κiを大きくしました。発声時の音の立ち上がりより、発音しなくなる場合の方が応答が早いと考えた為です。
 外乱として常に細かなビブラートと微細変動を付与しています。これは通常のボーカルの音声波形を見ても同様になっています。フレーズ末尾においてはビブラートの振幅を増大させて、ビブラートが明瞭に認識されるようにしました。

5、今後の課題
(1)プレパレーションの付与
 音程変化直前に観測される、音程変化とは逆方向の瞬時的な変化をプレパレーションと言います。現在のVocaSim にはプレパレーションが付与されていませんが、これを付与することで更に自然な発生が可能となると思われます。

(2)実際の発声を分析してフィードバック制御
 現在のVocaSimのフィードバックシステムは、VSQファイルを生成するところまでが対象です。実際のVocaloid2システムはDYN/PITに対して非線形かつ独自な応答をしますので、VocaSimが出力した音量・音高と実際の発声は異なっています。よって、Vocaloid2システムが出力する音声の音量と音高をフィードバック制御することで、ボーカル・システムを更に正確にシミュレーション可能となります。
(3)リアルタイムにΚp・Κiを変化
 現在のVocaSimは、曲の途中でΚp・Κiを変更できませんが、曲の途中でユーザがリアルタイムにΚp・Κiを制御することで、ユーザの演出意図を反映した音声シミュレーションが可能となります。

6、ライセンスについて
 当ソフトウエアの改変と再配布は自由で、特に作者への通知も必要ありません。但し、ウイルス・コード埋め込み、及びスパイウエアコードの埋め込み、その他法律に抵触する態様への改変を禁じます。


参考データと参考ソフトウエア
Dearest.vsq:ぼかんないんです>< yuukiss さん

【ニコニコ動画】【本気MEIKO】 Dearest (pf mix) 【カバー曲】

MikuMikuVoice:樋口優さん
http://www.geocities.jp/higuchuu4/index.htm
Ripples Ver.0.0.8:zhuoさん
http://www.geocities.jp/zhuoware/ripples/ripples_top.html

参考文献(敬称略)
VocaListenerユーザ歌唱を真似る歌声合成パラメータを自動推定するシステムの提案
中野倫靖, 後藤真孝(産業技術総合研究所) 2008/05
http://staff.aist.go.jp/t.nakano/PRESENTATION/pSIGMUS200805nakano.pdf

歌声知覚・生成機構の解明に向けた歌声合成システム構築に関する研究
斎藤毅 北陸先端科学技術大学院大学 情報科学研究科 2006/3
http://www.jaist.ac.jp/library/thesis/is-doctor-2006/abstract/t-saitou/jabstract.pdf

歌声における F0動的変動成分の抽出とF0制御モデルに関する研究
斎藤毅 北陸先端科学技術大学院大学 情報科学研究科 2002/2/15
http://www.jaist.ac.jp/library/thesis/is-master-2002/abstract/t-saitou/jabstract.pdf

歌声に含まれる基本周波数の微細変動成分の知覚に関する研究
北風裕教 北陸先端科学技術大学院大学 情報科学研究科 2000/2/15
http://www.jaist.ac.jp/library/thesis/is-master-2000/abstract/kitakaze/jabstract.pdf

| | コメント (2) | トラックバック (2)

VocaSim 0.0.3

今日は、日曜日の学会参加の分の代休ですので、VocaSim のコーディングをおこない、テスト用に「かもめのすいへいさん」の音楽データをピアプロにアップロードいたしました。

http://piapro.jp/content/vwczc758nihw5ee7

「かもめのすいへいさん」をミクがアカペラで歌うというものです。処理前と処理後を連結しましたので、簡単に処理の効果を比較いただけるかとおもいます。

「かもめのすいへいさん」の作詞家 武内俊子さん(1945年4月7日死去)作曲家 川村光陽(1946年死去)ともに死後50年が経過しており、よって著作権は消滅しています。

今回はコーディングよりも、「著作権消滅曲」をちゃんと探し当てるのが大変だったりします。(笑) 「とんぼのめがね」も「あかとんぼ」も「メリーさんの羊」もまだ著作権が消滅していないのですね。著作権が存在しない外国民謡に日本の作詞家が歌詞をつけるというパターンが多く、この場合には殆どが著作権が存続していますので、気をつけないといけませんね。

| | コメント (0) | トラックバック (0)

ぼかりすでない何か

「ぼかりすでない何か」のプログラムを作成中ですので、とりあえず現状の出来をアップロードします。

http://piapro.jp/content/ybx241dfo4hrpiwv

ミクがアカペラで「七つの子」を歌うというなんともベタなデモソングですが、使用前・使用後のVSQファイルでも見ていただければと思います。

ソフトウエアは、VocaSim と命名します。内部仕様ドキュメントを充実させ、音声のレベルアップを図ってアップロードする予定です。もちろんフリーソフトです。

| | コメント (1) | トラックバック (2)

miku_talk 0.2.1 のGUI化

 mashpodさんが、MIKU_TALK 0.2.1 をGUI化していただきましたので、ご紹介します。

http://mashpod.vox.com/library/posts/tags/miku_talk_gui/

 形態素解析エンジンを Yahoo!から mecab に変更されたり、サーバーサイドスクリプトをローカルPC用スクリプトに変更されたりするのは本当に大変だったろうと推定します。
 実は、サーバーの制限によりサーバーサイドスクリプトは処理できる文字数や形態素数がかなり少ないです。infoseek サーバーは最も処理できる文字数が多いサーバーのひとつですが、それでも2000文字程度(芥川龍之介の「蜘蛛の糸」の1/3)しか1回で処理できません。
 よって、ローカルPC用スクリプトである MIKU_TALK 0.2.1 のGUI版には、大量のデータを処理できるというアドバンテージがあると思われます。

| | コメント (0) | トラックバック (0)

「ぼかりす」への形態素解析の応用提案

ぼかりすの論文発表から、だいぶ経ってしまいましたが、これに対する形態素解析の応用を提案致したくおもいます。まず、VocaListener の全体像をご覧ください。

http://staff.aist.go.jp/t.nakano/image/VocaListenerFlow.pdf

 形態素解析は、歌詞を平仮名に変換する事のみに用いられています。論文に於いては「立ち止まる時、またふと振り返る」を「たちどまるときまたふとふりかえる」に変換するのみです。形態素解析で単語の区切り情報や品詞の種類などが含まれており、これを元に人間の歌唱に歌詞を当て嵌めれば、目標歌唱と歌詞(音素)の時間的対応付けが更に精確になると思われます。
 具体的な手順を以下に記載します。

(1) 歌詞を形態素解析する。(Yahoo!形態素解析の例)

立ち止まる    動詞,,,,,,,たちどまる,tachidomaru
時    名詞,,,,,,,とき,toki
また    副詞,,,,,,,また,mata
ふと    副詞,,,,,,,ふと,futo
振り返る    動詞,,,,,,,ふりかえる,furikaeru

(2) アラインメント用文法の生成
 単語区切り情報のノードを入れます。具体的には tachidomaru と toki の間、toki と mata の間などです。

(3) Viterbi アラインメント (各音素の始端と終端を推定)
 一定期間以上の発音間隔があったならば、単語の区切り情報のノードを割り当てます。発音の区切りは単語単位の区切りと一致することが多い為です。これによりフレーズを跨るなど大きな誤りは減少すると思います。

Vocalistener_00_2

 これが例となる音声波形です。青で示された部分に「一定期間以上の発音間隔」があります。よって、これらに当て嵌めることができる単語の組み合わせは以下のものです。

①「たちどまる」  「ときまたふりかえる」
②「たちどまるとき」  「またふとふりかえる」
③「たちどまるときまた」  「ふとふりかえる」
④「たちどまるときまたふと」  「ふりかえる」

 次に、①②③④のうち、どれを当て嵌めるのが最も確からしいかを算出します。一例として、母音の数と発音ピーク数の対応づけや、母音の数と発音期間の対応づけなどです。  この場合には青で示された部分より前には、おおむね7つの発音のピークが有るので、同様に7つの母音を有する②「たちどまるとき」が最も確からしいと推定できます。

 もし、この技術を Vocalistener に実装されるならば、謝辞に「アキバ系弁理士」と書いてください。(笑)

| | コメント (3) | トラックバック (0)

Silence

ちょっと見て出来に感動したので、備忘録代わりにブログに貼ります。

ニコニコ動画にもアップロードされていましたが、Zoomeの方がずっと画質が良く、ストレスなく鑑賞できました。

| | コメント (0) | トラックバック (0)

機械的イフェクトによるビブラート

 sih5632さんにビブラート機能を付加するDTMソフトウエアの情報をいただいたので、SONAR-7 のHPでビデオを見てみました。有益な情報をいただいたsih5632さんに感謝いたします。

・V-VocalのLFOツール
http://www.roland.co.jp/mov/page/SONAR7/index.htmlのビデオの中の「ボーカル・トラックの作成」
(LFOツールは「ボーカル・トラックの作成」のビデオのちょうど半分くらい時間が過ぎたあたりの「ビブラートをかけます」のあたりで紹介されています)

Sonar7_vibrato00
SONAR7 ホームページ「ボーカルトラックの作成」より引用

 ボーカル音声の音高(PIT)が表示されており、マウスで自由に曲線を変更することができ、またフラットに書き直したのちに指定範囲を正弦波に置き換えたり、その正弦波の振幅を次第に大きくしたりという、まさに想像した通りの機能が搭載されていました。

 元々の肉声ビブラートの音高(PIT)は青の選択範囲に於ける赤線で示された部分です。
人間のビブラート曲線は綺麗な正弦波とならないことがわかります。
Sonar7_vibrato01
SONAR7 ホームページ「ボーカルトラックの作成」より引用

なお、浜崎あゆみのCD「Dearest」は2001年度に発売されたもので、SONAR7は同じ2001年に発表されたDAWソフトウエアです。

AutoTuneにも同種の機能が搭載されているようです。
http://content3.e-frontier.co.jp/products/antares/at5/pro.html

オートマチックモードでは、ビブラートをサウンドに追加することもできます。
ビブラートセクションで、ビブラートの深さ、レート、ディレイをコントロールすることができます。
ビブラートのピッチのバリエーションを選択することもできます。(サイン波、ノコギリ波、矩形波など)。ビブラートを自分でかけられないボーカルの演奏に ビブラートを追加させるときなどにこのビブラートセクションが効果的です。また、特殊なサウンドを作成するときなどにも使用できます。
(AutoTune のホームページより引用)

| | コメント (3) | トラックバック (0)

ぼかんないんです><技法の解析

 浜崎あゆみの「Dearest」が入手できたので、歌声りっぷ 2.0 で浜崎あゆみボーカルを抜き出し、Ripples 0.0.8 で解析しました。Ripples を作成された zhuo さんに感謝いたします。解析結果は、いままでの推定が覆る意外な結果となりました。

1、音高(PIT)パラメータの解析
 浜崎あゆみボーカルと「ぼかんないんです><」のVSQファイルの「全て」の「て」のビブラート部分を抜き出し、PIT(音高)パラメータを縦軸に、横軸に時間として描画しました。

Subete_yks_ayu_pit_3
 浜崎あゆみボーカルのPIT(音高)パラメータは美しい正弦波を描いております。この正弦波は人間の生音声によるものではなく、機械イフェクトで加工されているのだと推定します。また、驚くべきことは「ぼかんないんです><」技法によるVSQファイルのPIT(音高)パラメータは、浜崎あゆみボーカルと振幅および位相がぴったりと一致しています。

 同様に両音声ファイルの「捨てて」の「て」のビブラート部分を抜き出し、PIT(音高)パラメータを縦軸に、横軸に時間として描画しました。こちらも極めてよく一致していることが判ります。

Sutete_yks_ayu_pit_2

2、音量(DYN)パラメータの解析
 浜崎あゆみボーカルと「ぼかんないんです><」のVSQファイルの「全て」の「て」のビブラート部分を抜き出し、DYN(音量)パラメータを縦軸に、横軸に時間として描画しました。 浜崎あゆみボーカルは高低差が少なかったため、パラメータに2.0を掛けて描画しました。

Subete_yks_ayu_dyn_2

 両音声ともに類似したカーブを描いていることが判ります。PIT(音高)パラメータほど一致しない理由は不明です。

 同様に両音声ファイルの「捨てて」の「て」のビブラート部分を抜き出し、DYN(音量)パラメータを縦軸に、横軸に時間として描画しました。浜崎あゆみボーカルは高低差が少なかったため、パラメータに2.0を掛けて描画しました。
 やはり、両音声ともに類似したカーブを描いていることが判ります。

Sutete_yks_ayu_dyn_2

3、結論
 「ぼかんないんです><」テクノロジーとは、原音声ファイルから音高パラメータと音量パラメータを機械的に抽出して、VSQファイルに反映させる技法と推定いたします。理由は、浜崎あゆみの原音声ファイルと「ぼかんないんです><」テクノロジーによる音声ファイルの音高パラメータと音量パラメータが極めて良く一致していることです。
 これまでは、「ぼかんないんです><」テクノロジーによって作られた音声ファイルの音高パラメータが極めて美しい正弦波だったので、浜崎あゆみ音声によるものではないと推定しておりました。しかし、浜崎あゆみ音声が機械イフェクトを掛けたものだったならば、ビブラート部分の音高(PIT)パラメータに「美しい正弦波」が出現することは納得できます。

4、浜崎あゆみの歌唱処理方法ノウハウについて
 浜崎あゆみのビブラートは、果たして機械イフェクトを掛けたものなのでしょうか。また、機械イフェクトを掛けたものであったならば、どのようなノウハウによって美しい歌唱を生成しているのでしょうか。
 そのようなノウハウが有ったならば、そのノウハウをVOCALOIDに搭載することで、単なる人間の音声の再現ではない「美しい歌声」を実現することが可能になると思われます。

追記:謎のテクノロジーだった「ぼかりす」を直感的に理解され、その一部といえども即日で再現いただき、VSQファイルを配布されたyuukissさんに感謝いたします。今後も引き続き Nostalogic のような名曲を発表いただければと思います。

| | コメント (1) | トラックバック (1)

MikuMikuVoice

音声ファイル(WAV)を入力してVSQファイルを出力し、初音ミクに歌わせるツールが現れました。その名はMikuMikuVoice。かの MikuMikuDance の作者である樋口さんの作品です。
http://www.geocities.jp/higuchuu4/index.htm

 歌詞(Lyric)はどう入力するかというと、時間範囲を指定して発音を手入力ですが、その指定時間範囲をループ再生させて確認できます。
 歌詞部分をどうするかというのは、WAV入力によるVSQ生成にとって大きな課題だったのですが、自動認識などで開発工数を膨らまさず、かつユーザーが歌詞部分を入力しやすいように、うまく処理していますね。

 既に「自分で歌って比較してみた」という方がおられましたので、紹介します。

VEL(ベロシティ)は固定値ですが、PIT(音高)とDYN(音量)は元音声をちゃんと反映させてあります。なおかつ note までちゃんと反映させているのが秀逸です。
これは単なるボイスチェンジャではない何かを感じます。これだけで何かうまい応用ができないものでしょうか。

| | コメント (0) | トラックバック (0)

ぼかんないんです><&ぼかりす

 「ぼかんないんです><」によって作成されたyuukiss氏の新作がアップロードされていたので、ご紹介します。


 音声の美しさもさることながら、Vocaloid Editor 上のPITとDYN の曲線の美しさに魅入ってしまいました。

 さて、昨日は神戸の学会での Vocalistener の発表のレポートが2ちゃんねるにレポートされていました。技術的要素は ①目標歌唱に近づけるため、合成歌唱の音高(PIT)パラメーター/音量(DYN)パラメーターを反復計算する事と、②目標歌唱と歌詞の時間的対応付けを自動化する事、及び③歌唱力を補正して歌をうまく聞こえるよう補正する事、以上3点です。

 yuukiss 氏がおこなったのは、①合成歌唱の音高パラメーター(PIT)/音量(DYN)パラメーター反復計算する事の代わりに、目標歌唱の波形を参照しながら手動でオートメーション描画した事と推定されます。詳しくは浜崎あゆみ「Dearest」を入手して波形を調査してみたく思います。波形調査にあたっては、zhuo さんの Ripples を使わせていただくと思います。便利な解析ツールを提供いただいた zhuo さんに感謝いたします。
 余談ですが、現在は浜崎あゆみ「Dearest」は在庫切れ欠品だそうで、やむを得ず Amazon で中古品を手配しているところです。

| | コメント (0) | トラックバック (0)

特開2002-221978の帰趨#3

 

特開2002-221978「ボーカルデータ生成装置、ボーカルデータ生成方法および歌唱音合成装置」とは、初音ミクに実装されていると思われる発明で、母音のタイミングを音符のタイミングと一致させる為に、子音を先行して発音させるものです。

【課題】 音節を構成する音素のうち、子音に対向する音素を音符の発生タイミングにあわせて発声することにより、伴奏に合わせたバーチャルシンガによる自然な歌唱を実現する。
【解 決手段】 歌詞に対応した音節毎の発音タイミングデータを含むボーカルデータを予め記憶する。再生処理を始めると、音符「ド」に対応した音節「さ」を発声させると き、子音「s」の発声動作を音符の発音タイミングよりも前に始め、母音「a」の発音タイミングを音符「ド」の発音タイミングに合わせる。これにより、伴奏 に遅れることなく、バーチャルシンガによる自然な歌唱を可能にする。

当該特許出願の、最初の拒絶理由通知(17条の2第1項1号)にて引用された発明 特開平10-319993 「データ編集装置」 の権利化後である特許3518253 「データ編集装置」 の請求項1を見てみました。特許発明の技術的範囲の判断は、原則として請求範囲が基準となるためです。(特許法70条1項) 括弧部分は請求項の理解のために付記しました。

【請求項1】

(公知部分1) 再生テンポに非依存のデュレーションデータにより発生時間が規定された複数の音素データから構成される音節データを含む音声データと

(公知部分2) 該音声データの発音タイミングを規定する再生テンポに依存したタイミングデータとを含むソングデータにおける

(公知部分3) 前記音節データを編集することができるデータ編集装置であって、

(特許要件1) 前記音節データを構成する前記複数の音素データのうちの1つを指定する音素指定手段と、

(特許要件2)
 前記音素指定手段により指定される音素データに対応するデュレーションデータを前記再生テンポの指定とは独立して指定される発生時間に変更する変更手段と

 を有するデータ編集装置。

特開平10-319993 の権利化後である特許3518253 「データ編集装置」 のデータ編集装置とは、Vocaloid Editor の編集機能などを指すと思われます。

 これを、特開2002-221978「ボーカルデータ生成装置、ボーカルデータ生成方法および歌唱音合成装置」の請求項1と対比します。

【請求項1】
(公知部分1) メロディおよび歌詞に対応するボーカルデータを生成するボーカルデータ生成装置であって、

(特許要件1) 歌詞の音節を前記メロディに対応する音符に割り当てる歌詞割当手段と、

(特許要件2) 前記音節を音素に分け、各音節を構成する音素のうち、母音の音素の発音タイミングを前記音符に対応する発音タイミングに合わせるべく各音節に対応する発音タイミングデータを生成する発音タイミングデータ生成手段と、

(特許要件3) 前記音節の音素列データ、前記発音タイミングデータおよび前記音節に対応した音高データをボーカルデータとして生成し、このボーカルデータを出力するデータ出力手段と、

 を備えたことを特徴とするボーカルデータ生成装置。

特開2002-221978 のボーカルデータ生成装置とは、Vocaloid Editor の音声出力機能を指すと思われます。最も大きな相違点は、引用発明は音素データの指定手段を有するのに対して、当該発明は音素データの指定手段が無い事です。
 出願人は、最初の拒絶理由通知に対する意見書で音素データの指定無しに発音タイミングを自動調整できることを主張しています。しかし、先願の特許要件を削除したならば、それは上位概念の発明となるため、拒絶査定(特許法49条)を受ける理由となると思います。
 出願人のヤマハ(株)は、Vocaloid の発声タイミングの自動調整機構は、特許3518253 「データ編集装置」 ではカバーされていないことに気づいたのだと思います。そして、特開2002-221978 を審査請求して特許権取得を狙ったが、特許3518253 「データ編集装置」 の権利化前である 特開平10-319993 「データ編集装置」で極めて近い発明が公知化されていた為、相違点は当業者に容易に想到できるとして審査官に拒絶査定を受けたのだと推定します。


 さて、今回の件で、特開平10-319993 「データ編集装置」 及び権利化後の特許3518253 「データ編集装置」 を見てみました。

H10319993_fig4
 これを Vocaloid1 Editor のPhonome編集画面と対比してみてください。酷似しているので驚いてしまいました。

 図4      - Phonome編集画面
 ノート     → (対応なし)
 発音時間   ⇔ POSITION
 歌詞      ⇔ LYRICS
 音素列データ ⇔ PHONETIC SYMBOLS
 呼気      → (対応なし)
 (対応なし)  ← PROTECT

Phenome_edit

段落0050は、ブレス音の実装を記載しています。Vocaloid2 の実装では、ブレスは音素として扱われていますが、当該発明では音素データの属性として扱われています。

【0050】呼気データ65は、息継ぎを表現することを示すデータである。音素データPDの後に呼気データ65が位置すると、その音素データPDを発音した後、息継ぎ表現を行うのため発音を無音状態に変化させることを示す。呼気データ65は、音素列データ55の最後に位置する場合に限らず、音素データPDと他の音素データPDの間に位置してもよい。

段落0052は、ベロシティ(VEL)の実装を記載しています。50音の音素ごとに子音の長さを調整するのではなく、更に細かな音素に分解し、その発音長(デュレーション)を変更可能としてます。

【0052】音節編集機能とは、該各音素のデュレーションを編集することができる機能である。例えば、音素「kha」のデュレーションを4×7.5msから、3×7.5ms又は5×7.5msに変更することができる。この機能を使えば、デュレーションを自由に設定することができるため、例えば音節「か」を発音する場合にも、多様な「か」の発音を行うことができる。

段落0053は、VOCALOIDには全く実装されていない機能について言及しています。

【0053】また、音節編集機能は、音節を構成する音素列データに新たな音素を付け加えることができる。例えば、音素列「CL+kha+aj」に新たな音素を付け加えることにより、鼻にかかったような「か」の発音を実現することも可能になる。さらに、音素を付け加える代わりに、音節を付け加えるようにしてもよい。

 上記のことを総合すると、特開平10-319993 「データ編集装置」 は、VOCALOID のプロトタイプを元に特許出願したものと推定します。VOCALOIDの編集ウインドウと酷似した画面が掲載されており、VOCALOIDに搭載された機能の多くが記載されており、かつVOCALOIDの技術発表(2003年)以前だからです。
 この推定が正しいとすると、特開平10-319993 「データ編集装置」の出願日の1997年5月22日には、既にVOCALOIDプロトタイプが開発済みであったことになります。

| | コメント (0) | トラックバック (0)

特開2002-221978の帰趨#2

特開2002-221978「ボーカルデータ生成装置、ボーカルデータ生成方法および歌唱音合成装置」とは、初音ミクに実装されていると思われる発明で、母音のタイミングを音符のタイミングと一致させる為に、子音を先行して発音させるものです。

【課題】 音節を構成する音素のうち、子音に対向する音素を音符の発生タイミングにあわせて発声することにより、伴奏に合わせたバーチャルシンガによる自然な歌唱を実現する。
【解 決手段】 歌詞に対応した音節毎の発音タイミングデータを含むボーカルデータを予め記憶する。再生処理を始めると、音符「ド」に対応した音節「さ」を発声させると き、子音「s」の発声動作を音符の発音タイミングよりも前に始め、母音「a」の発音タイミングを音符「ド」の発音タイミングに合わせる。これにより、伴奏 に遅れることなく、バーチャルシンガによる自然な歌唱を可能にする。

特開2002-221978が拒絶査定を受けたので、ヤマハ株式会社は拒絶査定不服審判(特121条)を請求し、同時に手続補正書を提出しました。最初の拒絶理由通知の「引用文献1のものはノートオン/オフのタイミングを直接かえて、このタイミングを実現しているが、これを、ノートオン/オフのタイミングは変えずに、音声波形の読み出し時期を制御することにより実現することは当業者が容易に発明をすることができたものである。」の意見に真っ向から反論しています。


【書類名】      手続補正書(方式)
【提出日】      平成17年 1月17日
【あて先】      特許庁長官 殿
【事件の表示】
  【審判番号】   不服2004-25743
  【出願番号】   特願2001- 19141
【補正をする者】
  【識別番号】   000004075
  【氏名又は名称】 ヤマハ株式会社
【代理人】
  【識別番号】   100098084
  【弁理士】
  【氏名又は名称】 川▲崎▼ 研二
  【電話番号】   03-3242-5481
【発送番号】     415026
【手続補正1】
 【補正対象書類名】 審判請求書
 【補正対象項目名】 請求の理由
 【補正方法】    変更
 【補正の内容】
  【請求の理由】
  【手続の経緯】
   出願            平成13年1月26日
   拒絶理由の通知(発送日)  平成16年6月8日
   意見書(提出日)      平成16年8月6日
   手続補正書(提出日)    平成16年8月6日
   拒絶査定(起案日)     平成16年11月8日
   同謄本送達(送達日)    平成16年11月16日
   手続補正書(提出日)    平成17年1月17日

  【拒絶査定の要点】
(a)原査定の拒絶理由は、本願の請求項1~8に係る発明は、特開平10-31999
3号公報(以下、引用例という)に記載された発明に基づいて、その出願前にその発明の
技術の分野における通常の知識を有する者が容易に発明をすることができたものであるか
ら、特許法第29条第2項の規定により特許を受けることができない、というものである

(b)その理由は、要するに、引用例には、音声波形を通常のノートオンタイミングで読
み出すと、子音の発音時間分だけ聴取者には発音が遅れたように聞こえる課題を解決する
ため、ノートオンのタイミングが母音の発音開始点となるように音声素片の読み出しタイ
ミングを調整することが記載されているため、本願発明は、この引用例に記載された発明
に基づき容易に発明することができたものである、というものである。
  【本願発明が特許されるべき理由】
(a)本願発明の説明
 請求項1に係る発明は、「メロディおよび歌詞に対応するボーカルデータを生成するボ
ーカルデータ生成装置であって、歌詞の音節のデータ数と前記メロディに対応する音符の
データ数とを合わせて、該歌詞の音節を該メロディに対応する音符に割り当てる歌詞割当
手段と、前記音節を音素に分け、各音節を構成する音素のうち、母音の音素の発音タイミ
ングが前記音符に対応する発音タイミングに合うように各音節の発音タイミングを指示す
る発音タイミングデータを生成する発音タイミングデータ生成手段と、前記音節の音素列
データ、前記発音タイミングデータおよび前記音節に対応した音高データをボーカルデー

タとして生成し、このボーカルデータを出力するデータ出力手段と、を備えたことを特徴
とするボーカルデータ生成装置」を要旨とするものである。
 かかる発明によれば、歌詞の音節のデータ数とメロディに対応する音符のデータ数とを
合わせて、該歌詞の音節を該メロディに対応する音符に割り当て、歌詞の音節を音素に分
け、母音の音素の発音タイミングが音符に対応する発音タイミングに合うように各音節の
発音タイミングを指示する発音タイミングデータを生成するので、操作者の手を全く煩わ
せることなく、歌詞に含まれる音節のうち子音および母音からなる音節のみを対象とし、
音符のタイミングより遅れて聞こえることのないよう自動的に音節の発音タイミングを調
整することができる。
 請求項2は、この請求項1におけるボーカルデータの出力態様に関し、「ボーカルデー
タをシステムエクスクルーシブメッセージに含ませて出力する」なる技術的限定を加えた
ものである。
 請求項3~6は、請求項1または2にさらなる技術的限定を加えて従属項、請求項7お
よび8は請求項1および2を各々方法のカテゴリに書き換えた請求項である。
(b)補正の根拠の明示
 同時に提出する手続補正書により、請求項1、2、7および8における歌詞割当手段ま
たは歌詞割当工程は、「歌詞の音節のデータ数と前記メロディに対応する音符のデータ数
とを合わせて、該歌詞の音節を該メロディに対応する音符に割り当てる」ものであること
を明らかにする補正を行った。この補正は、本願の出願当初の明細書における段落004
2の記載を根拠とするものである。
(c)引用発明の説明
 引用例の段落0060~0065には、音節毎に発音タイミングを早める程度を示すク
ロック数を定めた変換テーブルを記憶し、各音節の音声データの発生タイミングをその変
換テーブルに定められたクロック数だけ早める旨が開示されている。また、引用例の段落
0059および0060には、音節が音として聞こえるタイミングが子音のデュレーショ
ンにより遅れる旨が開示されている。また、引用例の段落0063には、子音の音素を含
まない音節については、発音タイミングを早める程度を示すクロック数を変換テーブルに
おいて定める必要がない旨が開示されている。
(d)本願発明と引用発明との対比
 引用発明は、子音のデュレーションにより聴取者には発音が遅れたように聞こえる課題
を解決するため、音節の発音タイミングを早めるものである点において、請求項1に係る
発明と共通の特徴を有する。

 しかしながら、請求項1に係る発明と引用発明との間には、次の相違点がある。すなわ
ち、請求項1に係る発明は、「音節を音素に分け、各音節を構成する音素のうち、母音の
音素の発音タイミングが前記音符に対応する発音タイミングに合うように各音節の発音タ
イミングを指示する発音タイミングデータを生成する」
に当たり、「歌詞の音節のデータ
数と前記メロディに対応する音符のデータ数とを合わせて、該歌詞の音節を該メロディに
対応する音符に割り当てる」という技術的特徴を有するのに対し、引用発明はこの技術的
特徴を有しない。
 音節には、母音のみからなる音節と、子音および母音のみからなる音節とがあるが、請
求項1に係る発明によれば、「歌詞の音節のデータ数と前記メロディに対応する音符のデ
ータ数とを合わせて、該歌詞の音節を該メロディに対応する音符に割り当てる」ため、各
音符には1つずつ音節が割り当てられ、それらのうち子音および母音からなる各音節につ
いては、「母音の音素の発音タイミングが前記音符に対応する発音タイミングに合うよう
に各音節の発音タイミングを指示する発音タイミングデータを生成する」ことができる。
このように請求項1に係る発明によれば、歌詞の中に含まれる音節のうち子音および母音
からなる音節のみを自動的に選択して調整対象とし、音符より遅れて聞こえることのない
ようにその音節の発音タイミングを調整することができる、という引用発明からは得られ
ない格別な効果が得られる。
このような特徴は、引用例には開示されておらず、示唆すら
されていない。

 よって、請求項1に係る発明は、引用発明に基づき容易に発明することができたもので
はなく、特許要件を具備すると確信する次第である。
 他の請求項に係る発明は、請求項1に係る発明にさらなる技術的限定を加えたもの、あ
るいは請求項1に係る発明のカテゴリのみを変更したものである。
 よって、これらの請求項に係る発明も、請求項1と同様の理由により、特許要件を具備
すると確信する次第である。
  【むすび】
 以上のように、本願発明は引用例に記載された発明とは全く別異であり、引用例から容
易には想到し得ないものであるから特許要件を具備するものと確信致します。よって本願
に対し、特許査定を賜りますようお願いする次第です。

これに対しての前置報告書は以下のものです。

                前置報告書

 審判番号         不服2004-25743
 特許出願の番号      特願2001-019141
 特許庁審査官       渡邊 聡         8622 5D00
 作成日          平成17年 2月23日

 この審判請求に係る出願については、下記の通り報告する。

                 記
 平成17年1月17日付け手続補正書にて新たに付加された構成(歌声生成時
に音符数と音節数とを対応させてメロディ付き音声を出力する点)は下記の周知
文献に記載されている。

本願出願前周知の技術事項を示す文献
特開2000-105595号公報

前置審査で、審査官は新たな先行技術として特開2000-105595「歌唱装置及び記録媒体」を指摘しました。出願人は日本ビクター株式会社です。この先行技術の要約を見てみます。

【課題】 任意のテキストファイルを自動的にメロディ にのせて歌にしてしまう歌唱装置がなかった。
【解決手段】 供給されるテキストデータはテキスト解析部4によってその音節データに変換され、供給されるテキストデータと共にメロディ 生成部6に出力される。また、音楽生成用SMF2aもメロディ 生成部6に出力される。そして、音節データは音楽生成用SMF2aのメロディ ーに割り当てられてシーケンサ部8に出力され、ソフトシンセ12によって、音節データを音声に変換して音程を変化させながらサウンド出力部14から出力する。

 VOCALOIDを先取りしたような発明を日本ビクターが出願していたものだと感心してしまいました。しかし、日本ビクターは、この発明が単発だったらしくてあとが続いていません。

 さて、拒絶査定不服審判は請求棄却審決となりましたが、その理由を見てみます。まずは引用発明との一致点と相違点を認定し、相違点について当業者が容易に想到することの論理を構築しております。このあたりは審査基準を厳格に守っていますね。

(一致点)
 「メロディおよび歌詞に対応するボーカルデータを生成するボーカルデータ生成装置であって、
 歌詞の音節のデータと前記メロディに対応する音符のデータとを合わせて、該歌詞の音節を該メロディに対応する音符に割り当てる歌詞割当手段と、
 前記音節を音素に分け、音節を構成する音素のうち、母音の音素の発音タイミングが前記音符に対応する発音タイミングに合うように音節の発音タイミングを指示する発音タイミングデータを生成する発音タイミングデータ生成手段と、
 前記音節の音素列データ、前記発音タイミングデータおよび前記音節に対応した音高データをボーカルデータとして生成し、このボーカルデータを出力するデータ出力手段と、
を備えたボーカルデータ生成装置。」
である点で一致し、次の各点で相違する。

(相違点1)
 本願補正発明は、歌詞の音節のデータ数とメロディに対応する音符のデータ数とを合わせて、歌詞の音節をメロディに対応する音符に割り当てているのに対し、引用例に記載された発明は、歌詞の音節のデータとメロディに対応する音符のデータとを合わせて、歌詞の音節をメロディに対応する音符に割り当てるものではあるが、歌詞の音節のデータ数とメロディに対応する音符のデータ数までを合わせるとは明記しない点。

(相違点2)
 本願補正発明は、各音節を構成する音素のうち、母音の音素の発音タイミングが音符に対応する発音タイミングに合うように各音節の発音タイミングを指示する発音タイミングデータを生成しているのに対して、引用例1に記載された発明は、音符の発生タイミングに対して発音の遅れを感じた歌詞(例えば、「か」)についてのみ音節の発生タイミングを指示して発音タイミングデータを生成している点。

(4)判断
(相違点1について)
 上記相違点1について判断するに、(i)通常、メロディを構成する音符の総数と歌詞を構成する音節の総数とは、ほぼ同数とされていることは、歌を愛好する人なら誰でも経験していることである。
(ii) また、メロディを構成する音符の総数と歌詞を構成する音節の総数とを、ほぼ同じ数とし、メロディが奏でられている間中、歌詞を歌唱することは、例えば、特開2000-105595号公報(特に、段落【0039】~【0041】の記載を参照。)にその旨の記載があるように当業者のみならず歌を愛好する人には周知自明な技術常識である。
 以上のことに鑑みると、引用例1に記載された発明に上記周知技術常識を適用して、本願発明の如く構成することは、当業者が適宜なし得ることである。

(相違点2について)
 上記相違点2について判断するに、(i)引用例1に記載されているように(前掲(ア)~(ウ)参照。)、音節が母音と子音からなる場合、母音の発声タイミングを音符の発生タイミングに合わせると音符が示す音の発生から遅れて、音節の音が聞こえる現象は、当分野の当業者の間に広く認識されている音現象であり、しかもこの問題を解消するためには音符の発生タイミングよりも子音の発声タイミングを少し前にずらせば解決すること(このことは人間が歌を歌うとき無意識に行っていることは、本願補正発明の明細書の段落【0004】における記載でも指摘されている。)も当業者の間に広く知られている自明な技術事項である。(ii)そして、引用例1に記載された発明は、音節及び音声データ編集時の操作性を高めるために、母音と子音とからなる音節すべてに対して等しく母音の発声タイミングを変更する構成を採用せず、敢えて、音符の示す音の発生から遅れを感じた歌詞のみに対して母音の発声タイミングを変更する構成を採用しているのであるから、音印象の如何にかかわらず一律に発声タイミングの変更を行うようにすることは、当業者が適宜なし得ることである。そして、その奏する効果の程も当業者の当初の予測の範囲を超えるものではない。

(5)むすび
 以上のとおり、本願補正発明は、引用例1に記載された発明及び周知技術に基づいて当業者が容易に発明をすることができたものであるから、特許法第29条第2項の規定により特許出願の際、独立して特許を受けることができるものではなく、特許法第17条の2第5項で準用する同法126条第5項の規定に違反するものであるから、平成17年1月17日付けの手続補正は、特許法第159条第1項で準用する同法第53条第1項の規定により却下すべきものである。

自分は、特開2000-105595「歌唱装置及び記録媒体」の図面に驚いてしまいました。まるで「初音ミク」の予言のように感じてしまいます。


20080514232703141204_2
20080514232703255814

 ついでに、最初の拒絶理由通知に記載された特開平10-319993 「データ編集装置」 を調べてみました。この特許の出願人はヤマハ(株)じゃないですか!しかも権利化されています。だったら、特開2002-221978 の権利化に拘らなくてもよかったのではと思います。

| | コメント (2) | トラックバック (0)

特開2002-221978の帰趨

特開2002-221978の帰趨について hidonさんからご質問を受けましたので、調査してみました。データベースは特許電子図書館の経過情報検索です。

特開2002-221978「ボーカルデータ生成装置、ボーカルデータ生成方法および歌唱音合成装置」とは、初音ミクに実装されていると思われる発明で、母音のタイミングを音符のタイミングと一致させる為に、子音を先行して発音させるものです。

【課題】 音節を構成する音素のうち、子音に対向する音素を音符の発生タイミングにあわせて発声することにより、伴奏に合わせたバーチャルシンガによる自然な歌唱を実現する。
【解 決手段】 歌詞に対応した音節毎の発音タイミングデータを含むボーカルデータを予め記憶する。再生処理を始めると、音符「ド」に対応した音節「さ」を発声させると き、子音「s」の発声動作を音符の発音タイミングよりも前に始め、母音「a」の発音タイミングを音符「ド」の発音タイミングに合わせる。これにより、伴奏 に遅れることなく、バーチャルシンガによる自然な歌唱を可能にする。

表1、特開2002-221978の経過情報

                                                                                                                                                                
出願記事特許 2001-019141 (平13.1.26) 出願種別(通常)
公開記事2002-221978 (平14.8.9)
発明の名称ボーカルデータ生成装置およびボーカルデータ生成方法
出願人ヤマハ株式会社 <YAMAHA CORPORATION>
発明・考案・創作者劔持 秀紀
公開・公表IPC
国際分類 第7版
   G10L 13/00         
国際分類 第4版
   G10L  3/00        J
出願細項目記事査定種別(拒絶査定)
審判記事登録記録査定不服審判 2004-025743 請求日(平16.12.16) 審判(判定含む) 請求不成立 最終処分日(平19.7.26)

この特許出願は、拒絶査定(特49条)を受けたのち、ヤマハ(株)は平成16年12月16日に拒絶査定不服審判(特121条)を請求しましたが、平成19年7月26日に請求棄却審決を受け、拒絶が確定したようです。よって、この特許出願は不成立のまま終わりました。

 最初の拒絶理由通知書は以下のものです。特開平10-319993号公報を理由に進歩性欠如(29条2項)で拒絶しています。

              拒絶理由通知書

 特許出願の番号      特願2001-019141
 起案日          平成16年 5月31日
 特許庁審査官       渡邊 聡         8622 5C00
 特許出願人代理人     川▲崎▼ 研二 様
 適用条文         第29条第2項


 この出願は、次の理由によって拒絶をすべきものである。これについて意見が
あれば、この通知書の発送の日から60日以内に意見書を提出して下さい。

                理 由

 この出願の下記の請求項に係る発明は、その出願前日本国内又は外国において
頒布された下記の刊行物に記載された発明に基いて、その出願前にその発明の属
する技術の分野における通常の知識を有する者が容易に発明をすることができた
ものであるから、特許法第29条第2項の規定により特許を受けることができな
い。

     記   (引用文献等については引用文献等一覧参照)
(請求項1乃至10について)
 下記の引用文献1には楽音合成装置において、ボーカル信号を合成するときの
タイミングについて、ボーカルの子音については人が聞き取りにくく、発音タイ
ミングは母音の発音開始時点に調整した方がよいことが記載されている。
 引用文献1のものはノートオン/オフのタイミングを直接かえて、このタイミ
ングを実現している
が、これを、ノートオン/オフのタイミングは変えずに、
声波形の読み出し時期を制御することにより実現すること
は当業者が容易に発明
をすることができたものである。
 上記以外の構成は、楽音発生装置の技術分野において周知の技術事項である。

 この拒絶理由通知書中で指摘した請求項以外の請求項に係る発明については、
現時点では、拒絶の理由を発見しない。拒絶の理由が新たに発見された場合には
拒絶の理由が通知される。

           引 用 文 献 等 一 覧
1.特開平10-319993号公報
------------------------------------
           先行技術文献調査結果の記録            
                                                                        
・調査した分野  IPC第7版  G10L13/00
                        DB名   
・先行技術文献                             
                                    
 この先行技術文献調査結果の記録は、拒絶理由を構成するものではない。

 これに対する2004年8月6日付けの意見書は以下のものです。先行技術文献が1件だけということは、審査官が相当の自信をもって拒絶理由通知を打ってきていると思われます。よって、出願人側は、本腰を入れて掛からないと特許を受けることはできません。
 しかし、出願人の代理人による意見書はなんだかベクトルがぶれている感じがします。当該発明の優位性を「音素の選択が不要である」ことならば、その点を重点的に述べて有利な効果を主張し、かつ補正により主張した点が明確になるようにすべきですが、そのような対処はなされていません。

【書類名】      意見書
【提出日】      平成16年 8月 6日
【あて先】      特許庁審査官 渡邊 聡 殿
【事件の表示】
  【出願番号】   特願2001- 19141
【特許出願人】
  【識別番号】   000004075
  【氏名又は名称】 ヤマハ株式会社
【代理人】
  【識別番号】   100098084
  【弁理士】
  【氏名又は名称】 川▲崎▼ 研二
  【電話番号】   03-3242-5481
【発送番号】     202468
【意見の内容】
(1)審査官殿は、本願の請求項1~10に係る発明は、その出願前に日本国内又は外国
において頒布された特開平10-319993号公報(以下、引例という)に記載された
発明に基づいて当業者が容易に発明することができたものであるから、特許法第29条第
2項の規定により特許を受けることができない、とのご認定である。
 しかしながら、本出願人は、この認定には承服できず、別紙手続補正書により本願発明
の要旨を明確にするとともに、以下に意見を申し述べる。
(2)本願の請求項1に係る発明は、別紙手続補正書により明らかにしたように「前記音
節を音素に分け、各音節を構成する音素のうち、母音の音素の発音タイミングが前記音符
に対応する発音タイミングに合うように各音節の発音タイミングを指示する発音タイミン
グデータを生成する」ものである。なお、この補正は、本願の出願当初の明細書の段落0
045、0053の記載および図面の図9を根拠としている。
 引例の段落0060~0065の記載によると、引例のものは、音節毎に発音タイミン
グを早める程度を示すクロック数を定めた変換テーブルを記憶し、子音の音素を含む音声
データの発生タイミングをその子音に対応したクロック数だけ早めるものである。しかも
引例によると、この子音に対応したクロック数だけ早める処理は、操作者が発音の遅れ
た歌詞(例えば「か」)を指定することにより行われる(段落0065)

 しかしながら、本願の請求項1に係る発明は、このように、操作者からの指示に従い、
変換テーブルを利用して、音声データの発生タイミングを早めるものではない。本願の請
求項1に係る発明の特徴は、「母音の音素の発音タイミングが音符に対応する発音タイミ
ングに合うように各音節の発音タイミングを指示する発音タイミングデータを生成する」
点にある。

 かかる発明によれば、音節が子音と母音からなる場合であっても、母音の発音タイミン
グが音符の発音タイミングに合ったボーカルデータが自動的に作成されるため、操作者の
手を全く煩わせることなく各音節の母音の発音タイミングが音符のタイミングとが整合し
たボーカルデータが得られる。

 このような技術的特徴は、引例には開示されておらず、示唆もされていない。他の独立
請求項2、7、8も同様である。
(3)結論
 従って、本願発明は特許要件を具備するものと確信致します。よって本願に対し、特許
査定を賜りますようお願いする次第です。

2004年8月6日付けの手続補正書は以下のものです。

【書類名】      手続補正書
【提出日】      平成16年 8月 6日
【あて先】      特許庁長官 殿
【事件の表示】
  【出願番号】   特願2001- 19141
【補正をする者】
  【識別番号】   000004075
  【氏名又は名称】 ヤマハ株式会社
【代理人】
  【識別番号】   100098084
  【弁理士】
  【氏名又は名称】 川▲崎▼ 研二
  【電話番号】   03-3242-5481
【発送番号】     202468
【手続補正1】
 【補正対象書類名】 明細書
 【補正対象項目名】 発明の名称
 【補正方法】    変更
 【補正の内容】
  【発明の名称】ボーカルデータ生成装置およびボーカルデータ生成方

【手続補正2】
 【補正対象書類名】 明細書
 【補正対象項目名】 特許請求の範囲
 【補正方法】    変更
 【補正の内容】
【特許請求の範囲】
  【請求項1】 メロディおよび歌詞に対応するボーカルデータを生成するボーカルデ
ータ生成装置であって、
 歌詞の音節を前記メロディに対応する音符に割り当てる歌詞割当手段と、
 前記音節を音素に分け、各音節を構成する音素のうち、母音の音素の発音タイミング
前記音符に対応する発音タイミングに合うように各音節の発音タイミングを指示する発音
タイミングデータを生成する発音タイミングデータ生成手段と、
 前記音節の音素列データ、前記発音タイミングデータおよび前記音節に対応した音高デ
ータをボーカルデータとして生成し、このボーカルデータを出力するデータ出力手段と、
を備えた
 ことを特徴とするボーカルデータ生成装置。
  【請求項2】 メロディおよび歌詞に対応するボーカルデータを生成するボーカルデ
ータ生成装置であって、
 歌詞の音節を前記メロディに対応する音符に割り当てる歌詞割当手段と、
 前記音節を音素に分け、各音節を構成する音素のうち、母音の音素の発音タイミング
前記音符に対応する発音タイミングに合うように各音節の発音タイミングを指示する発音
タイミングデータを生成する発音タイミングデータ生成手段と、
 前記音節の音素列データ、前記発音タイミングデータおよび前記音節に対応した音高デ
ータをボーカルデータとして生成し、このボーカルデータをシステムエクスクルーシブメ
ッセージに含ませて出力するデータ出力手段と、を備えた
 ことを特徴とするボーカルデータ生成装置。
  【請求項3】 請求項1または2記載のボーカルデータ生成装置において、前記デー
タ出力手段は、前記ボーカルデータをコーラス毎に分けて出力することを特徴とするボー
カルデータ生成装置。
  【請求項4】 請求項1または2記載のボーカルデータ生成装置において、前記デー
タ出力手段は、前記ボーカルデータをフレーズ毎に分けて出力することを特徴とするボー
カルデータ生成装置。
  【請求項5】 請求項1または2記載のボーカルデータ生成装置において、前記デー
タ出力手段は、前記ボーカルデータを各息継ぎ区間毎に分けて出力することを特徴とする
ボーカルデータ生成装置。
  【請求項6】 請求項1または2記載のボーカルデータ生成装置において、前記デー
タ出力手段は、前記ボーカルデータを小節毎に出力することを特徴とするボーカルデータ
生成装置。
  【請求項7】 メロディおよび歌詞に対応するボーカルデータを生成するボーカルデ
ータ生成方法であって、
 歌詞の音節を前記メロディに対応する音符に割り当てる歌詞割当工程と、
 前記音節を音素に分け、各音声を構成する音素のうち、母音の音素の発音タイミング
前記音符に対応する発音タイミングに合うように各音節の発音タイミングを指示する発音
タイミングデータを生成する発音タイミングデータ生成工程と、
 前記音節の音素列データ、前記発音タイミングデータおよび前記音節に対応した音高デ
ータをボーカルデータとして生成し、このボーカルデータを出力するデータ出力工程と、
を備えた
 ことを特徴とするボーカルデータ生成方法。
  【請求項8】 メロディおよび歌詞に対応するボーカルデータを生成するボーカルデ
ータ生成方法であって、
 歌詞の音節を前記メロディに対応する音符に割り当てる歌詞割当工程と、
 前記音節を音素に分け、各音声を構成する音素のうち、母音の音素の発音タイミング
前記音符に対応する発音タイミングに合うように各音節の発音タイミングを指示する発音
タイミングデータを生成する発音タイミングデータ生成工程と、
 前記音節の音素列データ、前記発音タイミングデータおよび前記音節に対応した音高デ
ータをボーカルデータとして生成し、このボーカルデータをシステムエクスクルーシブメ
ッセージに含ませて出力するデータ出力工程と、を備えた
 ことを特徴とするボーカルデータ生成方法。

【手続補正3】
 【補正対象書類名】 明細書
 【補正対象項目名】 0001
 【補正方法】    変更
 【補正の内容】
   【0001】
  【発明の属する技術分野】
 本発明は、例えばパソコンによるコンピュータ・ミュージックに用いて好適なボーカル
データ生成装置およびボーカルデータ生成方法に関する。

【手続補正4】
 【補正対象書類名】 明細書
 【補正対象項目名】 0010
 【補正方法】    変更
 【補正の内容】
  【0010】
 本発明は、以上の問題に鑑みてなされたものであり、伴奏に合わせたバーチャルシンガ
による自然な歌唱を実現することのできるボーカルデータを生成するボーカルデータ生成
装置およびボーカルデータ生成方法を提供することを目的としている。

【手続補正5】
 【補正対象書類名】 明細書
 【補正対象項目名】 0011
 【補正方法】    変更
 【補正の内容】
   【0011】
  【課題を解決するための手段】
 上記目的を達成するために、この発明は、歌詞の音節をメロディに対応する音符に割り
当て、音節を音素に分け、各音節を構成する音素のうち、母音の音素の発音タイミングが
音符に対応する発音タイミングに合うように各音節の発音タイミングを指示する発音タイ
ミングデータを生成し、音節の音素列データ、発音タイミングデータおよび音節に対応し
た音高データをボーカルデータとして生成するボーカルデータ生成装置およびボーカルデ
ータ生成方法を提供する。

 出願人が意見書で反論し、手続補正書で引用文献との差異を出そうとしたにも係わらず、審査官による拒絶査定を受けました。
 審査官は、進歩性(29条2項)を否定し得る論理として、「音素を選択せずに全てに処理を適用することは当業者にとって自明である」という点を指摘しており、当該拒絶査定は妥当とおもいます。

              拒絶査定


 特許出願の番号      特願2001-019141
 起案日          平成16年11月 8日
 特許庁審査官       渡邊 聡         8622 5D00
 発明の名称        ボーカルデータ生成装置およびボーカルデータ生
              成方法
 特許出願人        ヤマハ株式会社
 代理人          川▲崎▼ 研二


 この出願については、平成16年 5月31日付け拒絶理由通知書に記載した
理由によって、拒絶をすべきものである。
 なお、意見書並びに手続補正書の内容を検討したが、拒絶理由を覆すに足りる
根拠が見いだせない。

備考
 出願人は意見書にて下記のとおり主張している。
    記
 引例の段落0060~0065の記載によると、引例のものは、音節毎に発音
タイミングを早める程度を示すクロック数を定めた変換テーブルを記憶し、子音
の音素を含む音声データの発生タイミングをその子音に対応したクロック数だけ
早めるものである。しかも、引例によると、この子音に対応したクロック数だけ
早める処理は、操作者が発音の遅れた歌詞(例えば「か」)を指定することによ
り行われる(段落0065)。
 しかしながら、本願の請求項1に係る発明は、このように、操作者からの指示
に従い、変換テーブルを利用して、音声データの発生タイミングを早めるもので
はない。本願の請求項1に係る発明の特徴は、「母音の音素の発音タイミングが
音符に対応する発音タイミングに合うように各音節の発音タイミングを指示する
発音タイミングデータを生成する」点にある。
 かかる発明によれば、音節が子音と母音からなる場合であっても、母音の発音
タイミングが音符の発音タイミングに合ったボーカルデータが自動的に作成され
るため、操作者の手を全く煩わせることなく各音節の母音の発音タイミングが音
符のタイミングとが整合したボーカルデータが得られる。
 出願人の主張する、操作者が発音遅れの歌詞を指定する必要性については、引
用文献のものにおいて、
単にすべての歌詞を指定すれば本願発明のものと同じと
なることは自明のこと
であり、引用文献1のものは操作者の自由度を高めるため
に、あえて、遅れを感じた歌詞のみ指定できるようになっているのであるから、
あらかじめこのような機能を設けずにすべての歌詞について、一律に、発音タイ
ミングの変更を行うようにすることは当業者が適宜なしえたこと
である。
 そして、引用文献1にの【0059】、【0060】の記載を見れば、その技
術思想は、結局本願発明と同じ、音声波形を通常のノートオンタイミングで読み
出すと、子音の発音時間分だけ聴取者には発音が遅れたように聞こえる課題を解
決するため、ノートオンのタイミングが母音の発音開始時点となるように音声素
片の読み出しタイミングを調整することが記載されているから、本願発明は上記
拒絶理由通知書に記載された発明に基づき当業者が容易に発明をすることができ
たという拒絶の理由は解消していない。
                                 以上
続きは明日にでも記載します。

| | コメント (1) | トラックバック (0)

MIKU_TALK 0.2.1 ソース(VSQ生成部)

 MIKU_TALK 0.2.1 のVSQ生成部ソースを公開します。サーバ上のCGIスクリプトとして動作しますが、ローカルPC上で動くように変更するのは、それほど難しくはないと思います。説明なくとも理解できるよう、できるだけ沢山のコメントを入れました。これを参考に更に良いものが世の中に生み出されればと思います。

#!/usr/local/bin/perl
BEGIN { unshift(@INC, "/cgi-bin/lib"); }
########################################################################
#
#    Filename : miku_talk021.cgi @infoseek
#    Charcode : UTF-8
#
#    Released on 26/Apr/2008, Programmed by A.Izumi
#
#
use strict;
use CGI;
use CGI::Carp qw(fatalsToBrowser);
use Jcode;
use MIDI;        # MIDI-Perl のインストールを要する。(非標準モジュール)
#
#    プロバイダ固有部分:ワークファイルの相対書込み先
#
my $myWorkFolderPath = "work";

#
#    プロバイダ固有部分:URL
my $myUrl = "work";
my $myAdv = "";

$CGI::POST_MAX = 1024*1024*100;

#
#    ワークファイル書込みフォルダを作成しておく。
mkdir($myWorkFolderPath, 0777);

my $q = new CGI;
my $mySessionId = GetSessionId($q->remote_host);

my $myPostedString = $q->param("myText1");
my $myDebugMode    = $q->param("debug");

if( !defined($myDebugMode) ) {
  $myDebugMode = 0;
}
# 改行記号が \x0d の場合に \x0d\x0a に正規化する。
$myPostedString =~ s/\x0d\x0a/\x0d/g;
$myPostedString =~ s/\x0d/\x0d\x0a/g;
$myPostedString =~ s/%([0-9a-f][0-9a-f])/pack("C",hex($1))/egi;
$myPostedString = Jcode->new($myPostedString)->utf8;

#
#    入力された形態素のチェック
#
  my $maErrorLine = checkMa($myPostedString,$mySessionId);
  if( $maErrorLine > 0 ) {
    print $q->header(-type=>'text/html; charset=UTF-8');
    print $q->start_html(-lang=>'ja',
                     -charset  => 'UTF-8',
                     -encoding => 'UTF-8',
                     -title    => 'MIKU_TALK Ver. 0.2.0');
    print $myAdv, "\n";
    print $q->br;
    print $q->h1('MIKU_TALK はエラーを検出しました。'),
          $q->hr;
    print "MIKU_TALK は、".$maErrorLine."行目の形態素を読み取れません。\n";
    print $q->br;
    exit();
  }
  if( $myDebugMode != 0 ) {
    print $q->header(-type=>'text/html; charset=UTF-8');
    print $q->start_html(-lang=>'ja',
                     -charset  => 'UTF-8',
                     -encoding => 'UTF-8',
                     -title    => 'MIKU_TALK Ver. 0.2.0');
    print $myAdv, "\n";
    print $q->h1('MIKU_TALK がVSQファイルを生成しました。'),
          $q->hr,
          $q->br;
  }
  my $lockdir = "miku_lock";
  my $retry = 20;                            # リトライ回数セット
  while (!mkdir($lockdir, 0755)) {           # ロック作成。出来なければ待つ
    if (--$retry <= 0) {
       last;
    } # 20秒間ダメならあきらめて強行
    sleep(1);                              # 1秒待つ
  }
  my $myDebugPath = "./". $myWorkFolderPath. "/". $mySessionId. ".txt";
  my $myVsqPath = "./". $myWorkFolderPath. "/". $mySessionId. ".vsq";
  my $myVsqUrl  = $myUrl. "/". $mySessionId. ".vsq";

  WriteMA("ma000.txt",$myPostedString);
  $myPostedString = Hankaku2Zenkaku($myPostedString);
  WriteMA("ma001.txt",$myPostedString);
  $myPostedString = JoinTyouonKigou($myPostedString);
  WriteMA("ma002.txt",$myPostedString);
  $myPostedString = AddPhonetic($myPostedString);
  WriteMA("ma003.txt",$myPostedString);
  $myPostedString = AddSeparator($myPostedString);
  WriteMA("ma004.txt",$myPostedString);

  $myPostedString = ParseSentence($myPostedString);
  WriteMA("ma005.txt",$myPostedString);
  mecab2VsqGenerate( $myPostedString, $myVsqPath );

  my @myStatVsq = ();
  @myStatVsq = stat $myVsqPath;
  rmdir($lockdir);                           # ロックの削除

#
#    正常にVSQ生成できた。
#
  if( $myDebugMode != 0 ) {
#
#    デバッグモードでは、ダウンロードリンクを表示する。
#
    my $myVsqCgi = "miku_talk_dl021.cgi";
    $myVsqCgi   .= "?download_name=". $mySessionId. ".vsq";
    $myVsqCgi   .= "&source_path="  . $myVsqPath;
    $myVsqCgi   .= "&debug="        . $myDebugMode;
    print $q->a({href=> $myVsqCgi }, "VSQファイルのダウンロード");
    print $q->br;
    print "↑ ここをクリックしてください。";
    print $q->br;
    print $q->end_html;

  } else {
#
#    正常にVSQ生成できたなら、ダウンロードする。
#
    print $q->header(
        -content_type        => "audio/midi",
        -content_disposition => "attachment;filename=". $mySessionId. ".vsq"
      );
    my $contents;
    my @srcStat = stat $myVsqPath;

    open(hFile,"< ".$myVsqPath);
    binmode hFile;
    read hFile,$contents, $srcStat[7] + 1024;
    print $contents;
    close(hFile);
#
#    元ファイルは消す。
#
    unlink $myVsqPath;
  }
  exit;
########################################################################
#
#   サブルーチン名:WriteMA
#
#   第1引数:出力するファイルパス
#   第2引数:出力データ
#
sub WriteMA {
  open hFile,">".$_[0];
  my @myWords = split(/\n/, $_[1]);
  my $i=0;
  for($i=0; $i<@myWords-1; $i++) {
    print hFile $myWords[$i]."\n";
  }
  close hFile;
  return $_[1];
}
########################################################################
#
#   サブルーチン名:Hankaku2Zenkaku
#
#   形態素解析の読みが半角カナならば全角カナに変換する。
#
#    Mecab拡張形式入力
#    意味             :変数
#-------------------------------------------------
#    見出し            :$midasi
#    タブ区切り
#     0,品詞           :$hinsi
#     8,読み           :$yomi
#
sub Hankaku2Zenkaku {
  my @myWords = split(/\n/, $_[0]);

  my $i=0;
  for($i=0; $i<@myWords; $i++) {
    #
    # 現在着目している単語
    #
    my $thisWord = $myWords[$i];
    chomp($thisWord);
    $thisWord =~ s/\x0d//g;
    my( $midasi, $thisWord19 ) = (split( /\t/, $thisWord ))[0,1];

    if( !defined($thisWord19) || length($thisWord19)==0 ) {
      $myWords[$i] = sprintf("%s\x0d\n",$thisWord);
    } else {
      my( $hinsi, $yomi ) = (split( /,/, $thisWord19 ))[0,8];
#
#   Mecab対策・・・カタカナ記載は読みを出力しない場合があるので、
#  $midasi をそのまま読みとする。
#
      if( $hinsi eq "名詞" && $yomi eq "" ) {
        $yomi = $midasi;
      }
      my $yomi_sj = Jcode->new($yomi,'utf8')->sjis;
      $yomi = Jcode->new($yomi_sj,'sjis')->h2z->utf8;
      $myWords[$i] = sprintf("%s\t%s,,,,,,,,%s\x0d\n", $midasi, $hinsi, $yomi );
    }
  }
  my $result = "";
  for($i=0; $i<@myWords; $i++) {
    my $thisWord = $myWords[$i];
    $result .= $thisWord;
  }
  return $result;
}
########################################################################
#
#   サブルーチン名:JoinTyouonKigou
#
#    単独の長音記号を直前の語に付けて、発音を確定させる。
#
#    Mecab拡張形式入力
#    意味             :変数
#-------------------------------------------------
#    見出し            :$midasi
#    タブ区切り
#     0,品詞           :$hinsi
#     8,読み           :$yomi
#
sub JoinTyouonKigou {
  my @myWords = split(/\n/, $_[0]);

  my $i=0;
  for($i=0; $i<@myWords-1; $i++) {
#
# 現在着目している単語の各要素を切り出す。
#
    my $thisWord = $myWords[$i];
    chomp($thisWord);
    $thisWord =~ s/\x0d//g;
    my( $midasi, $thisWord19 ) = (split( /\t/, $thisWord ))[0,1];

    if( !defined($thisWord19) || length($thisWord19)==0 ) {
      $myWords[$i] = sprintf("%s\x0d\n",$thisWord);
    } else {
      my( $hinsi, $yomi ) = (split( /,/, $thisWord19 ))[0,8];

#
# 次に着目する単語が長音記号ならば、見出しと読みに追加してゆく。
#
      my $j=0;
      for($j=$i+1; $j<@myWords; $j++) {
        my $nextWord = $myWords[$j];
        chomp($nextWord);
        $nextWord =~ s/\x0d//g;
        my( $nextMidasi, $nextWord19 ) = (split( /\t/, $nextWord ))[0,1];
        if( length($nextWord19)!=0 ) {
          my( $nextHinsi, $nextYomi ) = (split( /,/, $nextWord19 ))[0,8];

          if( $nextMidasi eq "ー" || $nextMidasi eq "-" ) {
            $midasi .= $nextMidasi;
            $yomi   .= $nextMidasi;
            $myWords[$j] = "";
          } else {
            last;
          }
        }
      }
      $myWords[$i] = sprintf("%s\t%s,,,,,,,,%s\x0d\n", $midasi, $hinsi, $yomi );
    }
  }
  my $result = "";
  for($i=0; $i<@myWords; $i++) {
    my $thisWord = $myWords[$i];
    if( length($thisWord) != 0 ) {
      $result .= $thisWord;
    }
  }
  return $result;
}
########################################################################
#
#   サブルーチン名:AddPhonetic
#
#    機能:発音を付加する。
#
#    Mecab拡張形式入力
#    意味             :変数
#-------------------------------------------------
#    見出し            :$midasi
#    タブ区切り
#     0,品詞           :$hinsi
#     8,読み           :$yomi
#
#
#    Mecab拡張形式出力
#    意味             :変数
#-------------------------------------------------
#    見出し            :$midasi
#    タブ区切り
#     0,品詞           :$hinsi
#     8,読み           :$yomi
# ● 9,ミク発音と歌詞      :$lyricPhonetics
# ●10,発音数          :$phoneticCount
#
#
sub AddPhonetic {
  my @myWords = split(/\n/, $_[0]);
my %phonetic = (
"あ"=>"a",  "い"=>"i",   "う"=>"M",    "え"=>"e",    "お"=>"o",
"ぁ"=>"a",  "ぃ"=>"i",   "ぅ"=>"M",    "ぇ"=>"e",    "ぉ"=>"o",
"か"=>"k a","き"=>"k' i","く"=>"k M",  "け"=>"k e",  "こ"=>"k o",
"さ"=>"s a","し"=>"S i", "す"=>"s M",  "せ"=>"s e",  "そ"=>"s o",
"た"=>"t a","ち"=>"tS i","つ"=>"ts M", "て"=>"t e",  "と"=>"t o",
"な"=>"n a","に"=>"J i", "ぬ"=>"n M",  "ね"=>"n e",  "の"=>"n o",
"は"=>"h a","ひ"=>"C i", "ふ"=>"p\\ M","へ"=>"h e",  "ほ"=>"h o",
"ま"=>"m a","み"=>"m' i","む"=>"m M",  "め"=>"m e",  "も"=>"m o",
"や"=>"j a",             "ゆ"=>"j M",  "いぇ"=>"j e","よ"=>"j o",
"ら"=>"4 a","り"=>"4' i","る"=>"4 M",  "れ"=>"4 e",  "ろ"=>"4 o",
"わ"=>"w a","ゐ"=>"w i",
#        "ゑ"=>"w e",
"を"=>"o","うぃ"=>"w i",             "うぇ"=>"w e",
"ん"=>"n",
#"んが"=>"N a",   "んぎ"=>"N i",   "んぐ"=>"N M",   "んげ"=>"N e",   "んご"=>"N o",
#"んにゃ"=>"N' a","んにぃ"=>"N' i","んにゅ"=>"N' M","んにぇ"=>"N' e","んにょ"=>"N' o",

"が"=>"g a",   "ぎ"=>"g' i",  "ぐ"=>"g M",   "げ"=>"g e",   "ご"=>"g o",
"ざ"=>"dz a",  "じ"=>"dZ i",  "ず"=>"dz M",  "ぜ"=>"dz e",  "ぞ"=>"dz o",
"だ"=>"d a",   "ぢ"=>"dZ i",  "づ"=>"dz M",  "で"=>"d e",   "ど"=>"d o",
"ば"=>"b a",   "び"=>"b' i",  "ぶ"=>"b M",   "べ"=>"b e",   "ぼ"=>"b o",
"ぱ"=>"p a",   "ぴ"=>"p' i",  "ぷ"=>"p M",   "ぺ"=>"p e",   "ぽ"=>"p o",
"きゃ"=>"k' a","きぃ"=>"k' i","きゅ"=>"k' M","きぇ"=>"k' e","きょ"=>"k' o",
"しゃ"=>"S a", "しぃ"=>"S i", "しゅ"=>"S M", "しぇ"=>"S e", "しょ"=>"S o",
"ちゃ"=>"tS a","ちぃ"=>"tS i","ちゅ"=>"tS M","ちぇ"=>"tS e","ちょ"=>"tS o",
"にゃ"=>"J a", "にぃ"=>"J i", "にゅ"=>"J M", "にぇ"=>"J e", "にょ"=>"J o",
"ひゃ"=>"C a", "ひぃ"=>"C i", "ひゅ"=>"C M", "ひぇ"=>"C e", "ひょ"=>"C o",

"ふゃ"=>"p\\' a","ふぃ"=>"p\\' i","ふゅ"=>"p\\' M","ふぇ"=>"p\\' e","ふょ"=>"p\\' o",
"みゃ"=>"m' a","みぃ"=>"m' i","みゅ"=>"m' M","みぇ"=>"m' e","みょ"=>"m' o",
"りゃ"=>"4' a","りぃ"=>"4' i","りゅ"=>"4' M","りぇ"=>"4' e","りょ"=>"4' o",
"ぎゃ"=>"g' a","ぎぃ"=>"g' i","ぎゅ"=>"g' M","ぎぇ"=>"g' e","ぎょ"=>"g' o",
"じゃ"=>"Z a", "じぃ"=>"Z i", "じゅ"=>"Z M", "じぇ"=>"Z e", "じょ"=>"Z o",
"じゃ"=>"dZ a","じぃ"=>"dZ i","じゅ"=>"dZ M","じぇ"=>"dZ e","じょ"=>"dZ o",
"ぢゃ"=>"dZ a","ぢぃ"=>"dZ i","ぢゅ"=>"dZ M","ぢぇ"=>"dZ e","ぢょ"=>"dZ o",
"びゃ"=>"b' a","びぃ"=>"b' i","びゅ"=>"b' M","びぇ"=>"b' e","びょ"=>"b' o",
"ぴゃ"=>"p' a","ぴぃ"=>"p' i","ぴゅ"=>"p' M","ぴぇ"=>"p' e","ぴょ"=>"p' o",
"ふぁ"=>"p\\ a","ふぃ"=>"p\\ i","ふぅ"=>"p\\ M","ふぇ"=>"p\\ e","ふぉ"=>"p\\ o",
"てゃ"=>"t' a","てぃ"=>"t' i","てゅ"=>"t' M","てぇ"=>"t' e","てょ"=>"t' o",
"でゃ"=>"d' a","でぃ"=>"d' i","でゅ"=>"d' M","でぇ"=>"d' e","でょ"=>"d' o",
"ぁ"=>"h\\ a", "ぃ"=>"h\\ i",  "ぅ"=>"h\\ M","ぇ"=>"h\\ e", "ぉ"=>"h\\ o",
"っ"=>"tS  ",
"すぃ"=>"s i", "ずぃ"=>"dz i", "とぅ"=>"t M","どぅ"=>"d M",

"ア"=>"a",  "イ"=>"i",   "ウ"=>"M",    "エ"=>"e",    "オ"=>"o",
"カ"=>"k a","キ"=>"k' i","ク"=>"k M",  "ケ"=>"k e",  "コ"=>"k o",
"サ"=>"s a","シ"=>"S i", "ス"=>"s M",  "セ"=>"s e",  "ソ"=>"s o",
"タ"=>"t a","チ"=>"tS i","ツ"=>"ts M", "テ"=>"t e",  "ト"=>"t o",
"ナ"=>"n a","ニ"=>"J i", "ヌ"=>"n M",  "ネ"=>"n e",  "ノ"=>"n o",
"ハ"=>"h a","ヒ"=>"C i", "フ"=>"p\\ M","ヘ"=>"h e",  "ホ"=>"h o",
"マ"=>"m a","ミ"=>"m' i","ム"=>"m M",  "メ"=>"m e",  "モ"=>"m o",
"ヤ"=>"j a",             "ユ"=>"j M",  "イェ"=>"j e","ヨ"=>"j o",
"ラ"=>"4 a","リ"=>"4' i","ル"=>"4 M",  "レ"=>"4 e",  "ロ"=>"4 o",
"ワ"=>"w a","ヰ"=>"w i",
#        "ヱ"=>"w e",
"ヲ"=>"o",  "ウィ"=>"w i",             "ウェ"=>"w e",
"ン"    =>"n",
#"ンガ"  =>"N a", "ンギ"=>"N i",   "ング"=>"N M",   "ンゲ"=>"N e",   "ンゴ"=>"N o",
#"ンニャ"=>"N' a","ンニィ"=>"N' i","ンニュ"=>"N' M","ンニェ"=>"N' e","ンニョ"=>"N' o",
"ガ"=>"g a",   "ギ"=>"g' i",  "グ"=>"g M",   "ゲ"=>"g e",   "ゴ"=>"g o",
"ザ"=>"dz a",  "ジ"=>"dZ i",  "ズ"=>"dz M",  "ゼ"=>"dz e",  "ゾ"=>"dz o",
"ダ"=>"d a",   "ヂ"=>"dZ i",  "ヅ"=>"dz M",  "デ"=>"d e",   "ド"=>"d o",
"バ"=>"b a",   "ビ"=>"b' i",  "ブ"=>"b M",   "ベ"=>"b e",   "ボ"=>"b o",
"パ"=>"p a",   "ピ"=>"p' i",  "プ"=>"p M",   "ペ"=>"p e",   "ポ"=>"p o",
#                             "ヴ"=>""p M",
"キャ"=>"k' a","キィ"=>"k' i","キュ"=>"k' M","キェ"=>"k' e","キョ"=>"k' o",
"シャ"=>"S a", "シィ"=>"S i", "シュ"=>"S M", "シェ"=>"S e", "ショ"=>"S o",
"チャ"=>"tS a","チィ"=>"tS i","チュ"=>"tS M","チェ"=>"tS e","チョ"=>"tS o",
"ニャ"=>"J a", "ニィ"=>"J i", "ニュ"=>"J M", "ニェ"=>"J e", "ニョ"=>"J o",
"ヒャ"=>"C a", "ヒィ"=>"C i", "ヒュ"=>"C M", "ヒェ"=>"C e", "ヒョ"=>"C o",

"フャ"=>"p\\' a","フィ"=>"p\\' i","フュ"=>"p\\' M","フェ"=>"p\\' e","フョ"=>"p\\' o",
"ミャ"=>"m' a",  "ミィ"=>"m' i",  "ミュ"=>"m' M",  "ミェ"=>"m' e",  "ミョ"=>"m' o",
"リャ"=>"4' a",  "リィ"=>"4' i",  "リュ"=>"4' M",  "リェ"=>"4' e",  "リョ"=>"4' o",
"ギャ"=>"g' a","ギィ"=>"g' i","ギュ"=>"g' M","ギェ"=>"g' e","ギョ"=>"g' o",
"ジャ"=>"Z a", "ジィ"=>"Z i", "ジュ"=>"Z M", "ジェ"=>"Z e", "ジョ"=>"Z o",
"ジャ"=>"dZ a","ジィ"=>"dZ i","ジュ"=>"dZ M","ジェ"=>"dZ e","ジョ"=>"dZ o",
"ヂャ"=>"dZ a","ヂィ"=>"dZ i","ヂュ"=>"dZ M","ビェ"=>"dZ e","ビョ"=>"dZ o",
"ビャ"=>"b' a","ビィ"=>"b' i","ビュ"=>"b' M","ビェ"=>"b' e","ビョ"=>"b' o",
"ピャ"=>"p' a","ピィ"=>"p' i","ピュ"=>"p' M","ピェ"=>"p' e","ピョ"=>"p' o",
"ファ"=>"p\\ a","フィ"=>"p\\ i","フゥ"=>"p\\ M","フェ"=>"p\\ e","フォ"=>"p\\ o",
"テャ"=>"t' a", "ティ"=>"t' i", "テゥ"=>"t' M", "テェ"=>"t' e", "テォ"=>"t' o",
"デャ"=>"d' a", "ディ"=>"d' i", "デゥ"=>"d' M","デェ"=>"d' e",  "デォ"=>"d' o",
"ァ"=>"h\\ a", "ィ"=>"h\\ i",   "ゥ"=>"h\\ M", "ェ"=>"h\\ e",   "ォ"=>"h\\ o",
"ッ"=>"tS  ",
"スィ"=>"s i", "ズィ"=>"dz i", "トゥ"=>"t M","ドゥ"=>"d M",

","=>"br1","、"=>"br1", "。"=>"br2","!"=>"br2","?"=>"br2",
"("=>"br4","『"=>"br4","「"=>"br4"
);
  my $i=0;
  for($i=0; $i<@myWords; $i++) {
    #
    # 現在着目している単語
    #
    my $thisWord = $myWords[$i];
    chomp($thisWord);
    $thisWord =~ s/\x0d//g;
    my( $midasi, $thisWord19 ) = (split( /\t/, $thisWord ))[0,1];

    if( !defined($thisWord19) || length($thisWord19)==0 ) {
      $myWords[$i] = sprintf("%s\x0d\n",$thisWord);
    } else {
      my( $hinsi, $yomi ) = (split( /,/, $thisWord19 ))[0,8];
      my $lyricPhonetics = "";    # 歌詞と発音の構造体
      my $phoneticCount = 0;
#
# 読みに対応したミクの歌詞と発音記号の構造体を得る
#
      my $idxYomi;
      for($idxYomi=0; $idxYomi<(length($yomi)-1);) {
#
# UTF8 の3文字(9bytes)→2文字→1文字の優先順で
# カタカナとミクの発音テーブルから、発音記号を取得する。
#
        my $myLyric = "";
        my $myPhonetic = "";
        my $myLyricLen = 0;
        for($myLyricLen=9; $myLyricLen>=3; $myLyricLen-=3) {
          $myLyric = substr($yomi,$idxYomi,$myLyricLen);
          if( exists($phonetic{$myLyric}) ) {
            $myPhonetic = $phonetic{$myLyric};
            $phoneticCount++;
            last;
          } elsif( $myLyricLen<=3 ) {
            $myPhonetic = "";
            last;
          }
        }
        $idxYomi += $myLyricLen;
#
# 発音の直後が長音記号「ー」「-」のときは歌詞に長音記号を付加する。
#
        if( $myPhonetic ne "" ) {
          for(;;) {
            my $myLyric_appendix = substr($yomi,$idxYomi,3);
            if( $myLyric_appendix ne "ー" && $myLyric_appendix ne "-" ) {
              last;
            }
            $phoneticCount++;
            $myLyric .= $myLyric_appendix;
            $idxYomi += 3;
          }
          $lyricPhonetics .= $myLyric.":".$myPhonetic.";";
        } else {
          $lyricPhonetics .= ":;";
        }
      }
      $myWords[$i] = sprintf("%s\t%s,,,,,,,,%s,%s,%d\x0d\n",
        $midasi, $hinsi, $yomi, $lyricPhonetics, $phoneticCount );
    }
  }
  my $result = "";
  for($i=0; $i<@myWords; $i++) {
    my $thisWord = $myWords[$i];
    $result .= $thisWord;
  }
  return $result;
}
########################################################################
#
#   サブルーチン名:AddSeparator
#
#    区切りを入れる。
#
#    発音区切 "W575", 息継区切 "BR", 文末区切 "EOS"
#    区切りの場合にはタブ等は無く、そのまま改行記号が入る。
#
sub AddSeparator {
  my @myWords = split(/\n/, $_[0]);
  my $phoneticCountFromW575 = 0;
  my $myHinsiLast = "";

  my $i=0;
  for($i=0; $i<@myWords; $i++) {
#   
# 現在着目している単語の各要素を切り出す。
#   
    my $thisWord = $myWords[$i];
    chomp($thisWord);
    $thisWord =~ s/\x0d//g;
    my( $midasi, $thisWord19 ) = (split( /\t/, $thisWord ))[0,1];
    if( !defined($thisWord19) || length($thisWord19) == 0 ) {
#
#     区切りそのものだった場合は次の語の判断に入る
#
      $myHinsiLast = "";
      $phoneticCountFromW575 = 0;
      next;
    }
    if( $i == @myWords - 1) {
#
# 終端の単語は常に文末とする。
#
      $myWords[$i] = sprintf("%s\x0d\n%s\x0d\n", $thisWord, "EOS" );
      next;
    }
    my( $hinsi, $yomi, $lyricphonetics, $phoneticCount )
      = (split( /,/, $thisWord19 ))[0,8,9,10];
    $phoneticCountFromW575 += $phoneticCount;

    my $nextWord = $myWords[$i+1];
    chomp($nextWord);
    $nextWord =~ s/\x0d//g;
    my( $nextMidasi, $nextWord19 ) = (split( /\t/, $nextWord ))[0,1];

    if( (!defined($nextWord19) || length($nextWord19) == 0)
    &&    $nextMidasi eq "EOS" ) {
#    
#       既にMecabが文末 "EOS" を判定したら、新たな判定は不要。
#    
      next;
    }
    my( $nextHinsi ) = (split( /,/, $nextWord19 ))[0];

    my $mySeparator = "";
    if( $midasi eq "。" ||  $midasi eq "!" ||  $midasi eq "?" ) {
      $mySeparator = "EOS";
    } elsif( 0 <= index($lyricphonetics,"br") ) {
      $mySeparator = "BR";
    }
    if( length($mySeparator) == 0 ) {
      if( $phoneticCountFromW575 < 5 ) {
#
# 何もしない。
#
        ;
      } elsif( 5 <= $phoneticCountFromW575 && $phoneticCountFromW575 <= 7 ) {
#
# 5音節~7音節を発音し、かつ文節の頭となる単語だったら、そこで区切って発音する。
#
        if(($hinsi ne "名詞"     && $hinsi ne "形容詞" && $hinsi ne "形容動詞"
        &&  $hinsi ne "接頭詞"   && $hinsi ne "感動詞" && $hinsi ne "接頭辞"
        &&  $hinsi ne "副詞" )
        && ($nextHinsi eq "名詞"     || $nextHinsi eq "形容詞" || $nextHinsi eq "形容動詞"
        ||  $nextHinsi eq "接頭詞"   || $nextHinsi eq "感動詞" || $nextHinsi eq "接頭辞"
        ||  $nextHinsi eq "副詞" ) ) {
          $mySeparator = "W575";
        }
      } else {
#
# 発音があまりに長く8音節以上継続する場合には、次が名詞等(動詞を含む)ならば区切る。
#
        if(($nextHinsi eq "名詞"   || $nextHinsi eq "形容詞" ||  $nextHinsi eq "形容動詞"
        ||  $nextHinsi eq "接頭詞" || $nextHinsi eq "感動詞" ||  $nextHinsi eq "接頭辞"
        ||  $nextHinsi eq "副詞"   || $nextHinsi eq "動詞" ) ) {
          $mySeparator = "W575";
        }
      }
    }
    $myHinsiLast = $hinsi;
    $myWords[$i] = sprintf("%s\x0d\n", $thisWord );
    if( defined($mySeparator) && length($mySeparator) != 0 ) {
      $phoneticCountFromW575 = 0;
      $myHinsiLast = "";
      $myWords[$i] .= sprintf("%s\x0d\n", $mySeparator );
    }
  }
#
#
#
  my $result = "";
  for($i=0; $i<@myWords; $i++) {
    my $thisWord = $myWords[$i];
    if( length($thisWord) != 0 ) {
      $result .= $thisWord;
    }
  }
  return $result;
}
########################################################################
#
#   サブルーチン名:ParseSentence
#
#    文章全体を解析する。
#
#    Mecab拡張形式入力
#
#    意味             :変数
#-------------------------------------------------
#    見出し            :$midasi
#    タブ区切り
#     0,品詞           :$hinsi
#     8,読み           :$yomi
#   9,ミク発音         :$lyricPhonetics
#    10,発音数          :$phoneticCount
#
#    Mecab拡張形式出力(●部分)
#
#    意味             :変数
#-------------------------------------------------
#    見出し            :$midasi
#    タブ区切り
#     0,品詞           :$hinsi
#     8,読み           :$yomi
#   9,ミク発音         :$lyricPhonetics
#    10,発音数          :$phoneticCount
# ●11,文章終端までの形態素数  :$eosCount
# ●12,息継ぎまでの形態素数   :$brCount
# ●13,575区切りまでの形態素数:$w575Count
#
#
sub ParseSentence {
  my @myWords = split(/\n/, $_[0]);
  my $myEosCount  = 0;
  my $myBrCount   = 0;
  my $myW575Count = 0;

  my $i=0;
  for($i=@myWords-1; $i>=0; $i--) {
    #
    # 現在着目している単語
    #
    my $thisWord = $myWords[$i];
    chomp($thisWord);
    $thisWord =~ s/\x0d//g;
    my( $midasi, $thisWord19 ) = (split( /\t/, $thisWord ))[0,1];
    if( !defined($thisWord19) || length($thisWord19)==0 ) {
      if( $midasi eq "EOS" ) {
        $myEosCount  = 0;
        $myBrCount   = 0;
        $myW575Count = 0;
      } elsif( $midasi eq "BR" ) {
        $myBrCount   = 0;
        $myW575Count = 0;
      } elsif( $midasi eq "W575" ) {
        $myW575Count = 0;
      }
      $myWords[$i] = sprintf("%s\x0d\n",$thisWord);
    } else {
      my( $hinsi, $yomi, $lyricphonetics, $phoneticCount )
      = (split( /,/, $thisWord19 ))[0,8,9,10];

      $myWords[$i] = sprintf("%s,%d,%d,%d\x0d\n",
        $thisWord,$myEosCount,$myBrCount,$myW575Count );
      if( $phoneticCount != 0 && index($lyricphonetics,"br") < 0 ) {
        $myEosCount++;
        $myBrCount++;
        $myW575Count++;
      }
    }
  }
  my $result = "";
  for($i=0; $i<@myWords; $i++) {
    my $thisWord = $myWords[$i];
    $result .= $thisWord;
  }
  return $result;
}
########################################################################
#
# 現在のセッションを識別する文字列を生成する(年月日時分妙から生成)
# なお、hack されにくくするため末尾に8桁の乱数を付加する。
#
sub GetSessionId {
#  my $ss,$mn,$hh, $dd, $mm, $yy, $yb;
  my ($ss, $mn, $hh, $dd, $mm, $yy, $yb) = localtime(time);
  $yy += 1900;
  $mm++;
  my $mySessionId = sprintf("%04d%02d%02d%02d%02d%02d%08d",
    $yy, $mm, $dd, $hh, $mn, $ss, int(rand(99999999)));
  return $mySessionId;
}
########################################################################
#
#    形態素の正当性チェック:行が 'EOS' または TAB を含めば正当とする。
#    正当ならば 0、不当ならばエラー行番号を返すこと。
#
sub checkMa {
  my @myWords = split(/\n/, $_[0]);
  my $mySessionId = $_[1];

  my $lineNumber = 1;
  my $thisWord = "";
  foreach $thisWord (@myWords) {
    chomp($thisWord);
    if( substr($thisWord,0,3) eq "EOS" ) {
      next;
    }
    my( $midasi, $thisWord2 ) = (split(/\t/, $thisWord))[0,1];
    if( length($thisWord2) == 0 ) {
      return $lineNumber;
    }
    $lineNumber++;
  }
  return 0;
}
########################################################################
#
#   サブルーチン名:mecab2VsqGenerate
#
#   機能:Mecab 拡張形式からVSQファイルを生成する
#
#   第1引数:Mecabの出力
#   第2引数:出力VSQファイル名
#
#    Mecab拡張形式入力
#
#    意味             :変数
#-------------------------------------------------
#    見出し            :$midasi
#    タブ区切り
#     0,品詞           :$hinsi
#     8,読み           :$yomi
#   9,ミク発音         :$lyricPhonetics
#    10,発音数          :$phoneticCount
#    11,文章終端までの形態素数  :$eosCount
#    12,息継ぎまでの形態素数   :$brCount
#    13,575区切りまでの形態素数:$w575Count
#
#
sub mecab2VsqGenerate {
my @myWords = split(/\n/, $_[0]);
my $myVsqFile = $_[1];

#
# マスタートラックのイベント定義。
#
my @masterEvents = (
  ['track_name',    0, 'Master Track'],
  ['set_tempo',     0, 500_000], # 1qn = .50 seconds
  ['time_signature',0,4,2,24,8 ],
  ['end_track' ,    0],
);
#
# ミクの発音用テキストに於ける初期値の設定。
#
  my @myCommonSection =();
  push @myCommonSection, "[Common]";
  push @myCommonSection, "Version=DSB301";
  push @myCommonSection, "Name=Voice1";
  push @myCommonSection, "Color=181,162,123";
  push @myCommonSection, "DynamicsMode=1";
  push @myCommonSection, "PlayMode=1";

  my @myMasterSection =();
  push @myMasterSection, "[Master]";
  push @myMasterSection, "PreMeasure=4";

  my @myMixerSection =();
  push @myMixerSection, "[Mixer]";
  push @myMixerSection, "MasterFeder=0";
  push @myMixerSection, "MasterPanpot=0";
  push @myMixerSection, "MasterMute=0";
  push @myMixerSection, "OutputMode=0";
  push @myMixerSection, "Tracks=1";
  push @myMixerSection, "Feder0=0";
  push @myMixerSection, "Panpot0=0";
  push @myMixerSection, "Mute0=0";
  push @myMixerSection, "Solo0=0";

  my @myEventListSection =();
  push @myEventListSection, "[EventList]";
  push @myEventListSection, "0=ID#0000";

  my @myIDSection =();
  push @myIDSection, "[ID#0000]";
  push @myIDSection, "Type=Singer";
  push @myIDSection, "IconHandle=h#0000";

  my @myHandleSection =();
  push @myHandleSection, "[h#0000]";
  push @myHandleSection, "IconID=\$07010000";
  push @myHandleSection, "IDS=Miku";
  push @myHandleSection, "Original=0";
  push @myHandleSection, "Caption=";
  push @myHandleSection, "Length=1";
  push @myHandleSection, "Language=0";
  push @myHandleSection, "Program=0";

  my @myDynamicsBPListSection = ();
  push @myDynamicsBPListSection, "[DynamicsBPList]";

  my @myPitchBendBPListSection = ();
  push @myPitchBendBPListSection, "[PitchBendBPList]";

  my @myPitchBendSensBPListSection = ();
  push @myPitchBendSensBPListSection, "[PitchBendSensBPList]";
  push @myPitchBendSensBPListSection, "7680=6";

  my @mikuMidiEvents = ();
  push @mikuMidiEvents,['control_change' , 0, 0,  99, 96];

#
#  MIDIイベントを生成する。
#
  my $myPhoneticTotalCount = 0;    # 発音数のカウント
  my $pitch_normal = 120;        # 通常の発音期間 [mSEC]
  my $pitch_important = 180;    # 重要語の発音期間 [mSEC]
  my $pitch_bress = 240;        # 息継ぎの発音期間 [mSEC]
  my $note = 64;                # ノート(音の高さ)
  my $myIdPos = 7680;            # 発音タイミング [mSEC]
  my $myIdPosLast = $myIdPos;    # 直前の発音タイミング
  my $myHinsiLast = "";            # 直前の品詞
  my $myPitchBendInit  = 2400;    # ピッチベンドの初期値
  my $myPitchBend = $myPitchBendInit;    # ピッチベンドのベース
  my $myPitchBendHinsi = 0;                # 品詞毎のピッチベンドの差分
  my $myPitchBendDelta = 0;                # ピッチベンド変化量の初期値
  my $myLyricCount = 0;                    # 仮名文字数(息継ぎのため)
  my $myIsBress    = 0;                    # ブレスを使ったか
  my $myProminence = 1;                    # 発音のプロミネンスか?
  my $lastSeparator = "";
  my $nextSeparator = "";

  my $i=0;
  for($i=0; $i<@myWords; $i++) {
    my $thisWord = $myWords[$i];
    chomp($thisWord);
    $thisWord =~ s/\x0d//g;

    my( $midasi, $thisWord19 ) = (split( /\t/, $thisWord ))[0,1];
    if( !defined($thisWord19) || length($thisWord19) == 0 ) {
      $lastSeparator = $midasi;
      if( $lastSeparator eq "EOS" ) {
        $myProminence = 1;                    # 発音のプロミネンスか?
        $myIdPos += 240;                    # ブレスと文末に必要な間隔
        $myPitchBend = $myPitchBendInit;    # ピッチベンドの初期値。
      } elsif( $lastSeparator eq "BR" ) {
        $myProminence = 1;                    # 発音のプロミネンスか?
        $myIdPos += 120;                    # ブレスに必要な間隔
        $myPitchBend = $myPitchBendInit;    # ピッチベンドの初期値。
      } elsif( $lastSeparator eq "W575" ) {
        $myProminence = 1;                    # 発音のプロミネンスか?
        $myIdPos += 60;                        # 575区切りに必要な間隔
        if( $myPitchBend < -3600 ) {
          $myPitchBend = 0;    # ピッチベンドの初期値。
        }
      }
      next;
    }
    my( $hinsi,
        $yomi,
        $lyricPhonetics,
        $phoneticCount,
        $eosCount,
        $brCount,
        $w575Count ) = (split( /,/, $thisWord19 ))[0,8,9,10,11,12,13];

    my $nextWord = $myWords[$i+1];
    chomp($nextWord);
    $nextWord =~ s/\x0d//g;
    my( $nextMidasi, $nextWord19 ) = (split( /\t/, $nextWord ))[0,1];
    if( !defined($nextWord19) || length($nextWord19) == 0 ) {
      $nextSeparator = $nextMidasi;
    } else {
      $nextSeparator = "";
    }
#
# 記号の区切りであったとき。
#
    if( $nextSeparator eq "BR" || $nextSeparator eq "EOS" ){
#
# 無音期間を設ける
#
      $myIdPos += 120;                    # ブレスに必要な間隔
      $myPitchBend = $myPitchBendInit;    # ピッチベンドの初期値。
    }
    if( $midasi eq "「" || $midasi eq "『" || $midasi eq "(" ) {
       if( $note < 70 ) { # E5 の音階は88
         $note += 1;
       }
    }
    if( $midasi eq "」" || $midasi eq "』" || $midasi eq ")" ) {
       if( 64 < $note ) {    # A3 の音階は69
         $note -= 1;
       }
    }
#
# 特殊(記号)でかつ発音がなければ、1文字分の期間をおく。
#
    if(($hinsi eq "特殊" || $hinsi eq "記号")
    &&  $phoneticCount == 0 ) {
      $myIdPos += 120;
      next;
    }
#
# 品詞ごとの音量を規定する。
#
    if( $hinsi eq "名詞" ) {
      push @myDynamicsBPListSection, ($myIdPos)."=80";
    } elsif( $hinsi eq "形容詞" || $hinsi eq "形容動詞"
    ||  $hinsi eq "接頭詞" || $hinsi eq "感動詞" || $hinsi eq "接頭辞"
    ||  $hinsi eq "副詞" ) {
      push @myDynamicsBPListSection, ($myIdPos)."=72";
    } else {
      push @myDynamicsBPListSection, ($myIdPos)."=64";
    }

#
# 読みに対応したミクの発音記号を得る。
#
    my $lyricCount = 0;
    my @eachLyricPhonetics = split( /;/, $lyricPhonetics );
    my $thisLyricPhonetic = "";
    foreach $thisLyricPhonetic (@eachLyricPhonetics) {
      my ($thisLyric, $thisPhonetic ) = split(/:/,$thisLyricPhonetic);
      my $myLength = 120;
#
#     文末の「。?!」は長く息継ぎする。
      if( $nextSeparator = "EOS" && substr($thisPhonetic,0,2) eq "br" ) {
        $myLength = 240;
      }
#
#    長音記号があったならば、その分は長く発音する。
#
      if( 0 < index($thisLyric,"ー",0) ) {
        $myLength *= (length($thisLyric) - index($thisLyric,"ー",0))/3 + 1;
        $thisLyric = substr($thisLyric,0,index($thisLyric,"ー",0));
      } elsif( 0 < index($thisLyric,"-",0) ) {
        $myLength *= (length($thisLyric) - index($thisLyric,"-",0))/3 + 1;
        $thisLyric = substr($thisLyric,0,index($thisLyric,"-",0));
      }
#
# 語尾ならば、ピッチを下げて発音する。
#
      if( $eosCount == 0 ) {
        $myPitchBendDelta = -400;
        $myPitchBendHinsi = -3600;
        if( $nextMidasi eq "?" && $lyricCount == $phoneticCount - 1) {
#
# 疑問文のときは語尾を上げる。
#
          $myPitchBendDelta = +400;
        }
      } elsif( $brCount == 0 ) {
#
# もし、ブレス直前だったならばトーンを落とす。
#
        $myPitchBendHinsi = -3600;
        $myPitchBendDelta = -400;
      } else {
#
# もし、以下の品詞だったならば、自然な音節の下降を付与する。
#
        if( $hinsi eq "名詞"   || $hinsi eq "形容詞" || $hinsi eq "形容動詞"
        ||  $hinsi eq "接頭詞" || $hinsi eq "感動詞" || $hinsi eq "接頭辞"
        ||  $hinsi eq "副詞" ) {
          $myPitchBendDelta = -200;
          $myPitchBendHinsi = 0;
          if( $hinsi eq "名詞" && $lyricCount == 0 && 2 < $phoneticCount && $myLength == 120) {
            $myPitchBendDelta = +400;
          }
        } else {
          $myPitchBendDelta = -200;
          $myPitchBendHinsi = -1200;
          if( $w575Count == 0 ) {
            $myPitchBendHinsi = -2400;
          }
        }
      }

      if( $myProminence == 1 ) {
        $myPitchBendDelta = +400;
        $myProminence = 0;
      }

      if( $thisPhonetic ne "" ) {
        push @myEventListSection, sprintf("%d=ID#%04d",$myIdPos,$myPhoneticTotalCount+1);
        push @myIDSection, sprintf("[ID#%04d]",$myPhoneticTotalCount+1);
        push @myIDSection, "Type=Anote";
        push @myIDSection, "Length=".$myLength;
        push @myIDSection, "Note#=".$note;
#       if( $myPhoneticTotalCount == 0 ) {

#
# か行、が行、さ行、ざ行、「つ」はベロシティを大きく(子音を短く)
#
        my @phonetic_array  = split(/ /, $thisPhonetic);
        my $myConsonant = $phonetic_array[0];
        if( $myConsonant eq "k" || $myConsonant eq "g"
        ||  $myConsonant eq "s" || $myConsonant eq "dz" || $myConsonant eq "dZ"
        ||  $thisPhonetic eq "ts M") {
          push @myIDSection, "Dynamics=80";
        } elsif( $myConsonant eq "4" ) {
#
# ら行はベロシティを小さく(子音を長く)
#
          push @myIDSection, "Dynamics=20";
        } else {
          push @myIDSection, "Dynamics=50";
        }
          push @myIDSection, "PMBendDepth=6";          #20";
          push @myIDSection, "PMBendLength=0";
          push @myIDSection, "PMbPortamentoUse=0";
          push @myIDSection, "DEMdecGainRate=0";    #50";
          push @myIDSection, "DEMaccent=4";        #50";
#       }
        push @myIDSection, sprintf("LyricHandle=h#%04d", $myPhoneticTotalCount+1);
        push @myHandleSection, sprintf("[h#%04d]", $myPhoneticTotalCount+1);
        push @myHandleSection, "L0=\"". Jcode->new($thisLyric,'utf8')->sjis
          ."\",\"". $thisPhonetic."\",1.000000,64,0,0";

        if( substr($thisPhonetic,0,2) eq "br" ) {
          $myPitchBend = $myPitchBendInit;        # ピッチベンドの初期値
        } else {
          my $myLocalId = 0;
          for($myLocalId = 0; $myLocalId<$myLength; $myLocalId += 120 ) {
            $myPitchBend += $myPitchBendDelta*2;
            if( $myPitchBend < -8192 ) {
              $myPitchBend = -8192;
            } elsif( 8191 < $myPitchBend ) {
              $myPitchBend = 8191;
            }
            my $myPitchBendOut = $myPitchBend + $myPitchBendHinsi;
            if( $myPitchBendOut < -8192 ) {
              $myPitchBendOut = -8192;
            } elsif( 8191 < $myPitchBendOut ) {
              $myPitchBendOut = 8191;
            }
            push @myPitchBendBPListSection, ($myIdPos+$myLocalId)."=".$myPitchBendOut;
          }
        }
        $myIdPos += $myLength;
        if( $myPhoneticTotalCount == 0 ) {
          push @mikuMidiEvents,['control_change', 5760, 0, 99,  80];
        } else {
          push @mikuMidiEvents,['control_change', $myIdPos - $myIdPosLast, 0, 99,  80];
        }
        $myPhoneticTotalCount++;
      } else {
#       発音できない記号は、単に時間間隔を空ける。
        $myIdPos += $myLength;
      }
      $myIdPosLast = $myIdPos;
      $lyricCount++;
    }
    $myHinsiLast = $hinsi;
  }
  push @mikuMidiEvents,['end_track' , $pitch_normal+1920];
  push @myEventListSection, sprintf("%d=EOS",$myIdPos);
#
#  ミク発音用メタデータのセクションを結合する
#
  my $my_miku_phonetics="";
  my $phonetic = "";
  foreach $phonetic (@myCommonSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myMasterSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myMixerSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myEventListSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myIDSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myHandleSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myDynamicsBPListSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myPitchBendBPListSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myPitchBendSensBPListSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
#
#  Voice1トラックのイベントを生成する。
#
my @voice1Events = (
  ['track_name',    0, 'Voice1'],
);
  for($i=0; $i*119<length($my_miku_phonetics); $i++) {
    push @voice1Events, ['text_event', 0,
      sprintf("DM:%04d:",$i).substr($my_miku_phonetics,$i*119,119) ];
  }
  my $mikuMidi = "";
  foreach $mikuMidi (@mikuMidiEvents) {
    push @voice1Events,$mikuMidi;
  }
#
# マスタートラックとVoice1トラックからVSQファイルを生成する。
#
  my $master_track = MIDI::Track->new({ 'events' => \@masterEvents });
  my $voice1_track = MIDI::Track->new({ 'events' => \@voice1Events });
  my $opus = MIDI::Opus->new(
    { 'format' => 1, 'ticks' => 480, 'tracks' => [ $master_track, $voice1_track ] } );
  $opus->write_to_file( $myVsqFile );
}

 なお、サーバー上で同プログラムを動かすためには、サーバー上に MIDI-Perl のファイル、CGIのモジュール及びJcodeのモジュールが必要です。infoseek はデフォルト状態では MIDI-Perl が存在しませんので、以下のファイルをサーバ上に転送しました。

(1) \cgi-bin 直下に MIDI.pm 及び Jcode.pm を転送する。
(2) \cgi-bin\MIDI に Event.pm, Opus.pm, Score.pm, Simple.pm, Track.pm, Filespec.pod を転送する。

| | コメント (2) | トラックバック (1)

400P=yuukiss氏のVSQファイルの解析#5

 zhuoさんが作成されたツール "Ripples 0.0.8" を使って、①人間の歌声のビブラート ②初音ミクのビブラート機能 ③400P=yuukiss氏の「ぼかんないんです><」 それぞれの音程(PIT)と音量(DYN)のグラフを描いて、②と③どちらが人間の歌声に近いか考察してみました。グラフの縦軸は音量(DYN)または音程(PIT)で、横軸は全て時間です。
 以下のグラフは Ripples 0.0.8 のテキスト出力を Excelでグラフ化したものです。Ripples を作成された zhuoさんに感謝いたします。

①人間の歌声のビブラート
 音量(DYN)と音程(PIT)は、約10Hzの正弦波であり、その振幅は次第に大きくなっています。これがビブラートとして認識されると判断いたします。時間が経過すると共に音量(DYN)と音程(PIT)は次第に下降します。これは人間の生理現象によるものです。
Mydearest_subete_dyn
Mydearest_subete_pit

②初音ミクのビブラート機能
 音量(DYN)には殆ど振幅は存在せず、音程(PIT)に約20Hzの弱い振幅が見られます。これがビブラートとして認識されると判断いたします。音量(DYN)と音程(PIT)ともに山なりのカーブを描き、全体として下降カーブを示します。
Miku_default_subete_dyn
Miku_default_subete_pit

③400P=yuukiss氏の「ぼかんないんです><」

 音量(DYN)と音程(PIT)は、約11Hzの綺麗な正弦波であり、その振幅は次第に大きくなっています。これがビブラートとして認識されると判断いたします。時間が経過すると共に音量(DYN)と音程(PIT)は次第に下降しており、人間の生理現象によるものを上手くシミュレートしています。

Vocannaidesu_subete_dyn
Vocannaidesu_subete_pit

 総合的に見て、②初音ミクのビブラート機能 よりも、③「ぼかんないんです><」の技法 の方が明瞭にビブラートを認識できると判断いたします。③はビブラートの振幅が明瞭で、周波数が人間の(自分の)ビブラートに近いからです。

 従来のVOCALOID向け楽曲の、ビブラートの効きが悪い部分に「ぼかんないんです><」技法を適用することで、ビブラート効果の改善が見込めると思われます。

| | コメント (0) | トラックバック (0)

400P=yuukiss氏のVSQファイルの解析#4

 zhuoさんが作成されたツール "Ripples 0.0.8" を使って、人間の歌声、特にビブラートがどのようなグラフを描くかを見てみました。ここに、Ripples を作成された zhuoさんに感謝いたします。
 本当は浜崎あゆみの生ボーカルが分析できるとよかったのですが、CDからボーカルをきれいに抽出できなかったので、やむをえず自分で(笑)歌ってみたものを分析しました。歌詞「すべて」の「」の部分にビブラートが聞こえているので、人間の歌唱のビブラートの実験サンプルとしては使えると思います。
 分析した歌声に対応する歌詞は「すべて」で、3つの発音要素を含み、音量(DYN)と音程(PIT)に対応する部分があります。全体として音量(DYN)と音程(PIT)が極めて高い相関を示す事発音要素の区切りごとに音量(DYN)の谷間がある事などもわかります。これらは400P=yuukiss氏の調教法の特徴でもあります。
 3番目の発音要素「」は音量(DYN)が約10Hzで振動しており、これがビブラートとして聞こえることが判ります。また、この振動波形は正弦波からほど遠い「汚い」波形であることに着目すべきです。音程(PIT)は目立った振動は見当たりません。これは自分の歌唱力の無さによるものか、それとも人間の歌唱はこのようなものなのかは不明です。また、音量(DYN)は右肩下がりとなっておりますが、これは肺の空気量が少なくなると音量が下がるという生理的現象によるものと思われます。

Mydearest_subete_cut

図1、自分の歌唱の音量(DYN)音程(PIT)

 次に、400P=yuukiss氏の VSQファイルに対応するWAVファイルを解析してみました。VSQファイルの音量(DYN)と音程(PIT)のパラメータがWAVファイル上にどのように反映されるかを見る事と、400P=yuukiss氏の VSQファイルのビブラートが、Ripples上にどのように反映されるかを見る事が目的です。

400_dyn_subete
図2、400P=yuukiss氏のVSQファイルのDYN(音量)

400_pit_sutete
図3、400P=yuukiss氏のVSQファイルの音階(PIT)

Subete
図4、400P=yuukiss氏のVSQファイルの音量(DYN)音程(PIT)

 Vocaloid Editor 上の音量(DYN)と音階(PIT)はWAVファイル上に精確に表されている事と、音量(DYN)のカーブは人間の(自分の)発音とほぼ一致している事が判ります。しかし、3番目の発音要素「」の音程は、約11Hzの綺麗な正弦波を描いており、人間の(自分の)音程とやや相違します。この相違点の理由は不明です。

結論:
 400P=yuukiss氏のVSQファイルは、人間の歌唱から変換したものではないと判断します。人間の歌唱を変換したならば綺麗な正弦波とはならない為です。400P=yuukiss氏は、人間の歌唱音の音程と音階を詳細に分析し、VSQファイル上に何らかの方法で再構成したのだと判断します。

| | コメント (0) | トラックバック (1)

Nostalogic

今日のiPod BGM はこちらを聞いてました。

「ぼかりす」の発表から間もなく、耳コピした曲を発表されるというのは只者ではないとは思っておりました。このオリジナル曲「 Nostalogic 」は、バックはやはり自らキーボードで演奏されたのでしょうか。

 もう少し400氏=yuukiss氏のVSQを解析をしてみます。発音要素の時間長さが100mSEC台のときのDYN/PITグラフを描いておらず、「ぼかんないんです><」の技法が完全には理解できていないのです。

 当該ブログをHPで紹介いただいておりまずzhuoさんも、400氏=yuukiss氏の手法の再現に挑戦しておられます。

Ripples 0.07

 既にツールまで作っておられるのがスゴイ! 果たして 「Dearest」の音程と音量はどうなっていたのでしょうか? 時間が出来たらすぐに、CDを買って Ripples の人柱となって試したいところです。

| | コメント (0) | トラックバック (0)

vocannaindesu

 当ブログで、謎の神調教師「400氏」のVSQファイル解析結果を記載しておりましたが、その400氏=yuukiss氏が動画をアップロードされ、当技術を「ぼかんないんです><」と命名されました。


 結局、このVSQファイルがどのような素性で出来上がったかのかは明示されていないのですが、「ぼかりす」を聞いた印象が、「あ、それってOKだったんですか」「じゃあ自分も一度やっちゃおうかな」というところから、何らかのスクリプトで自動生成したか、もしくは原曲の情報をツールで抜き出したのではないかと推定します。詳しくは次の「初音ミク」の作品のコメントを待ちたいと思います。

 自分としては、以下のコメントでニヤニヤしたり。

400_douga00

 yuukiss氏が、自らピアノを演奏できたりするのが、ちょっと羨ましかったり。

 来週から自分の子供をヤマハ音楽教室に通わせるので、付き添い「ついで」に自分もキーボードをこっそり練習しようかと考えています。

| | コメント (0) | トラックバック (0)

特開2002-221978

 400氏のVSQ解析中に、特開2002-221978「ボーカルデータ生成装置、ボーカルデータ生成方法および歌唱音合成装置」が、初音ミクに実装されている証拠らしきデータを得ました。特開2002-221978の要約を以下に引用します。

【課題】 音節を構成する音素のうち、子音に対向する音素を音符の発生タイミングにあわせて発声することにより、伴奏に合わせたバーチャルシンガによる自然な歌唱を実現する。
【解 決手段】 歌詞に対応した音節毎の発音タイミングデータを含むボーカルデータを予め記憶する。再生処理を始めると、音符「ド」に対応した音節「さ」を発声させると き、子音「s」の発声動作を音符の発音タイミングよりも前に始め、母音「a」の発音タイミングを音符「ド」の発音タイミングに合わせる。これにより、伴奏 に遅れることなく、バーチャルシンガによる自然な歌唱を可能にする。

 こちらが初音ミクの「あ [a]」の発音波形の図で、横軸が時間[秒]で縦軸が音声の振幅です。凡そ8.058秒から発音が始まっており、主たる母音は 8.070秒から発音されていることがわかります。

A_wav00_2
図1、初音ミクの「あ」の発音波形

 こちらは、全く同じタイミングで初音ミクが「か [ka] 」を発音したときの波形です。8.047秒から高い周波数成分の発音が始まり、8.070秒まで続き、その後に低い周波数成分が続きます。高い周波数成分は子音の[k]で、低い周波数成分は母音の[a]と思われます。
 この推測が正しいならば、初音ミクの子音成分は母音成分よりも先に発音されており、特開2002-221978に記載された発明が、初音ミクに実装されていると確認できたことになります。

Ka_wav00
図1、初音ミクの「か」の発音波形

| | コメント (1) | トラックバック (0)

400氏のVSQファイルの解析#3

 まずは最初に前回の解析結果に関する修正報告です。

 Vocaloid2 Editorは任意時間長の入力ができます。左上のLength と Quantize 双方ともにOFFにすると、任意時間長の入力が可能であることを確認いたしました。(下図参照)コメントいただいたkmさんに感謝いたします。400氏のVSQファイルに、30の倍数以外の時間長が記載されていたとしても、何ら不思議ではありません。よって、これだけの証拠で400氏が Vocaloid2 Editor を使用していないと推定したのは、やや勇み足でした。

 

Vocaloid2editor_off_off
図1、任意時間長を入力できる設定 (Length/Quantize 双方とも off)

 今回は、400氏のVSQファイルのうちPIT(ピッチベンド・音程)と、DYN(ダイナミックス・音量)について調査してみました。400氏がどのように神調教を実現し、VSQファイルを生成したかを知るためです。

1、パラメータ調査結果について
1)PIT(ピッチベンド・音程)
 横軸を時間[mSEC]、縦軸をピッチベンド(PIT)とし、400氏のVSQファイル中の歌詞「たいせつなあ」の「なあ」の部分を赤色で描き歌詞「すてて」の2番目の「て」の部分を青色で描いたものです。
 どちらも正弦波カーブが描かれており、これがビブラートとして人間に認識されます。赤色のグラフと青色のグラフの振幅と周期は極めて良く一致します。これだけ正確な正弦波を複数箇所で人間が描けるとは考えにくいです
 また、赤色のグラフは下端の-8192でクリップされていることに着目すべきです。
人間がVocaloid2 Editor でパラメータを描画した場合、下端でクリップされることは避けて描画すると思われます。 
400_pend500_pit_2
 こちらは、発音長が300mSEC~400mSEC の場合の発音要素(基本的に仮名1文字の発音)の PIT(ピッチベンド)の正弦波曲線です。周期が極めて良く一致していることが判ります。それぞれ微妙な周期ずれが有る理由は不明です。
400_pend300_pit

2)DYN(ダイナミックス・音量)
 文節の先頭・中間・末尾種別で、発音要素(仮名文字1文字)のDYN(ダイナミックス)のカーブが相違します。最初に文節の先頭部分をご覧ください。

 黄色の曲線が「ほんとうに」の「ほ」の発音要素、赤色の曲線が「もおのいがい」の「も」の発音要素、青色の曲線が「すてて」の「す」の発音要素のDYN(ダイナミックス)のカーブです。
 赤青黄の曲線すべてが発音要素の30mSECほど前から立ち上がっています。VOCALOIDは楽譜の母音のタイミングが楽譜のタイミングと一致させるため、子音を早めに発音している事と関係すると推定しました。子音の発音が始まる前からDYN(ダイナミックス)を上げておかないと、子音部分が聞き取れず、母音部分のみが強調された不自然な歌唱となります
 試しに初音ミクのデフォルト状態で「か」と「あ」を発音させた場合、「か」の方が20mSEC先に発音が始まりました。デフォルトの初音ミクでは子音は20mSEC先行して発音が始まるようですので、それを見越してDYN(ダイナミックス・音量)を調整する必要があります。
 また、400氏のVSQファイルは次の発音に入る直前に50mSEC程度、DYN(ダイナミックス・音量)を絞っています。これにより、人間が発音要素ごとに区切って喋るさまを表したのではと思います。
 赤青の曲線は良く一致していますが。黄色の曲線はやや他と乖離しています。この理由は不明です。
400_ptop_dyn

 文節の中間部分の発音要素のDYNグラフをご覧ください。グラフ形状が極めて良く相似します。 次の発音に入る直前に50mSEC程度、DYN(ダイナミックス・音量)を絞っている様子が観察できます。水色の曲線はやや他と相違していますが、その理由は不明です。
400_pmid_dyn
 文節の末尾部分の発音要素のDYNグラフをご覧ください。ビブラートを表す正弦波曲線と共に右方下がりの曲線となっていますが、肺の中の空気量が少なくなるにつれ音量が下がるという人間の生理現象を表現していると思われます。
400_pend_dyn

2、まとめ
 400氏は、Vocaloid2 Editor のパラメータ描画機能は使っていないと推定します。フリーハンドで描画したにしては、PIT(ピッチベンド・音程)の曲線が綺麗すぎ、周期が精確すぎるからです。また、人間がパラメータを描画した場合、PIT(ピッチベンド)の下端でクリップされることは避けて描画すると思われるからです。
 400氏は、WAVファイルをVSQ変換していないと推定します。人間の歌唱ファイルを元に変換したにしては、PIT(ピッチベンド・音程)の曲線が綺麗すぎ、かつ周期が精確すぎるからです。
 では、400氏はどうやってこの VSQファイルを作成したのでしょうか? そして400氏と「ぼかりす」とは何らかの関係を有しているのでしょうか?

3、400氏へのメッセージ
 PIT(ピッチベンド)の下端クリップや上端クリップを避ける為には、PBS(ピッチベンドセンシティビティ)の値を2に設定し、PIT(ピッチベンド)の値を半分にすればOKです。ご参考までに。

追記:400氏がまた書込まれていたようです。
http://pc11.2ch.net/test/read.cgi/streaming/1209997849/

716 名前:何スレか前の400 本日のレス 投稿日:2008/05/06(火) 08:57:45 U0wKRW7z0 ?

>>686 >>687 >>691 >>694
あー、mp3は消してしまいました。
調声もまだ途中だったし、カラオケ音源を使ったものを
いつまでも残しておくのもアレったので。

進捗状況ですが、MEIKOさんと初音ミクさんの音源はとりあえず完成しました。
今はMEIKOさんの動画をしこしこ制作中です。
実は、同時公開予定のオマケ(?)のほうが先に出来上がってしまったという。

「同時公開予定のオマケ?」とは、もしかして400氏流のDYN/PIT調整ツールでしょうか?

| | コメント (0) | トラックバック (0)

400氏のVSQファイルの解析#2

 400氏のVSQファイルの解析で見逃していたことがありましたので、ご報告します。

 まず最初に、Vocaloid2 Editor で作成したと思われるVSQファイル「奇跡の海」 Ver.1.1 の冒頭部を示します。Length (発音時間 [mSEC])は全て30の倍数となっており、この楽曲の場合のVocaloid2 Editor の最小時間設定単位が30mSECであったと思われます。

奇跡の海 Ver.1.1 のVSQファイルはこちらです。
http://www9.uploader.jp/dl/tukuru_koubou/tukuru_koubou_uljp00004.zip.html

[ID#0001]
Type=Anote
Length=60
Note#=62
Dynamics=63
PMBendDepth=5
PMBendLength=1
PMbPortamentoUse=0
DEMdecGainRate=3
DEMaccent=3
LyricHandle=h#0001
[ID#0002]
Type=Anote
Length=480
Note#=63
Dynamics=96
PMBendDepth=5
PMBendLength=1
PMbPortamentoUse=3
DEMdecGainRate=3
DEMaccent=3
LyricHandle=h#0002
VibratoHandle=h#0003
VibratoDelay=161
[ID#0003]
Type=Anote
Length=720
Note#=71
Dynamics=64
PMBendDepth=5
PMBendLength=1
PMbPortamentoUse=0
DEMdecGainRate=3
DEMaccent=3
LyricHandle=h#0004
[ID#0004]
Type=Anote
Length=180
Note#=68
Dynamics=64
PMBendDepth=5
PMBendLength=1
PMbPortamentoUse=0
DEMdecGainRate=3
DEMaccent=3
LyricHandle=h#0005
[ID#0005]
Type=Anote
Length=30
Note#=68
Dynamics=0
PMBendDepth=5
PMBendLength=1
PMbPortamentoUse=0
DEMdecGainRate=3
DEMaccent=3
LyricHandle=h#0006
[ID#0006]
Type=Anote
Length=180
Note#=70
Dynamics=64
PMBendDepth=5
PMBendLength=1
PMbPortamentoUse=3
DEMdecGainRate=3
DEMaccent=3
LyricHandle=h#0007

次に、400氏のVSQファイルのメタテキストの一部をご覧ください。Lengthの値を太字にいたしました。

[ID#0021]
Type=Anote
Length=239
Note#=61
Dynamics=64
PMBendDepth=0
PMBendLength=0
PMbPortamentoUse=0
DEMdecGainRate=50
DEMaccent=50
LyricHandle=h#0021
[ID#0022]
Type=Anote
Length=147
Note#=66
Dynamics=79
PMBendDepth=0
PMBendLength=0
PMbPortamentoUse=0
DEMdecGainRate=50
DEMaccent=50
LyricHandle=h#0022
[ID#0023]
Type=Anote
Length=361
Note#=64
Dynamics=87
PMBendDepth=0
PMBendLength=0
PMbPortamentoUse=0
DEMdecGainRate=50
DEMaccent=50
LyricHandle=h#0023
[ID#0024]
Type=Anote
Length=250
Note#=61
Dynamics=63
PMBendDepth=0
PMBendLength=0
PMbPortamentoUse=0
DEMdecGainRate=50
DEMaccent=50
LyricHandle=h#0024
[ID#0025]
Type=Anote
Length=122
Note#=64
Dynamics=72
PMBendDepth=0
PMBendLength=0
PMbPortamentoUse=0
DEMdecGainRate=50
DEMaccent=50
LyricHandle=h#0025
[ID#0026]
Type=Anote
Length=676
Note#=66
Dynamics=93
PMBendDepth=0
PMBendLength=0
PMbPortamentoUse=0
DEMdecGainRate=50
DEMaccent=50
LyricHandle=h#0026

 Vocaloid2 Editor は、縦が音階、横が時間を表す升目からなり、発音の長さなどは、設定最小単位以下は設定できませんし、任意時間長をVocaloid2 Editor 入力する方法は、寡聞にして知りません。
 しかし、上記のように400氏のVSQファイルは、発音の長さを任意に設定しています。
 よって、自分のVocaloid2 Editor に係る知識が不足しているのでなければ、400氏は Vocaloid2 Editor 以外の方法で、このVSQファイルを作成したと思われます。
 どのような方法でこのVSQファイルを作成したのでしょうか? 専用MIDIプログラム? それとも専用の変換ソフトウエア? そして400氏の正体は誰なのでしょうか?

| | コメント (2) | トラックバック (0)

中野さん-後藤さんのコメント

VocaListener の作者であらせられる:中野倫靖さん, 後藤 真孝さんのコメントがWEBに掲載されています。これで「ぼかりす=VocaListener」であることが確定しました。
http://staff.aist.go.jp/m.goto/VocaListener/index-j.html

2008年5月28日~29日に開催される 音楽情報科学研究会 にて学会発表予定の

      VocaListener: ユーザ歌唱を真似る歌声合成パラメータを自動推定するシステムの提案
      中野 倫靖, 後藤 真孝 (産総研)

のデモンストレーション動画の一部を、試験的に 【初音ミク】 PROLOGUE 【ぼかりす】 に掲載させて頂きました。(以下略)

この論文の筆頭執筆者の中野倫靖さんは、全く特許出願はヒットしませんでしたが、論文を検索すると幾つかヒットします。ずいぶん若い方なのかな?

・Voice Drummer:口ドラムでドラムを叩く楽譜入力インタフェース …… 101
 中野倫靖*,後藤真孝**,緒方淳**,平賀譲*
 *筑波大学図書館情報メディア研究科.**産業技術総合研究所
http://www.interaction-ipsj.org/archives/paper2005/pdf2005/interactive/A152.pdf

組織名から見ると、中野倫靖さんが筑波大学の学生だった頃のものでしょう。代表図を以下に引用します。
Voicedrummerping

3つの色分けされた領域のうち、オレンジ部分はドラム用の原楽譜、緑色部分は演奏者が「ドン」「トン」などを口頭で喋ることによって演奏された履歴、青色部分は演奏者の口頭での喋り部分が表示されます。何となく初音ミクのピアノロールエディタっぽいですね。

中野さんの技術専門分野は、音楽情報処理(音楽音響信号処理)で、学生の頃の研究でビブラート部分の自動検出などを試されていたようです。(以下図参照)
Nakano_00
中野さんはプライベートでは、筑波大学の管弦楽団でバイオリン奏者として活躍されていましたが、ヤマハ(株)の剣持秀樹さんも同様に管弦楽団でバイオリン奏者として活躍されています。音楽関係の研究者の趣味とは似通うものですね。

| | コメント (2) | トラックバック (1)

400氏のVSQファイル解析

 初音ミクみくの記事「出た!VocaListenerの秘密の一端解明か?謎の調教師が置き土産!」を見て、さっそく問題のVSQファイルを解析してみました。これにより、更に初音ミクの楽曲が高度なものとなれば幸いです。

 謎の調教師を仮に「400氏」と呼びます。400は初出のレス番号から由来するものです。

 「400氏」は噂の「ぼかりす」と匹敵するような高品質な初音ミクの歌声を作成してアップロードされ、歌声の元となるVSQファイルもアップロードされました。「400氏」のVSQファイルはこちらです。

http://www.42ch.net/UploaderSmall/source/1209596322.zip
pass=miku

(1)デフォルト歌唱スタイル

デフォルト歌唱スタイルですが、何も初期設定から変わっていません。

400_setting_2

 VEL(ベロシティ)/DYN(ダイナミックス)/PIT(ピッチベンド)のパラメータが操作されています。それ以外のBRE/BRI/CLE/GEN/POR/PBSは初期値のままです。

(2)VEL(ベロシティ)の操作の意味について

 VEL(ベロシティ)は子音の発音の強さで、小さいほど子音が強く表現されます。

 400氏のVSQファイルは、音節の最初ほどVEL(ベロシティ)が小さく、後ろにゆくほど大きくなっています。すなわち、文節の最初は子音を強く発音させ、文節の終端ほど子音を弱く発音させています。人間は文節ごとに息継ぎをします。息継ぎ後には強く発音されていた子音が、文節の終端ほど段々小さく発音されていく様を表したものとおもいます。

400_vel

(3)DYN(ダイナミックス)について
 DYN(ダイナミックス)は音量です。この値が大きければ音量が大きくなります。

 400氏のVSQファイルは、ある程度短い発音要素「す」は山なりに段々と大きくし、「べ」など極めて短い発音要素は極めて鋭い山なりにしています。
 特徴的なのは、ある程度長い発音要素の場合には、しだいに大きくなる正弦波カーブを描くことです。この正弦波によってビブラートを実現していると推定します。
 また、音節全体でゆるやかな山なりのカーブを描いている点も着目すべきです。ここでは「すべて」の山なりのカーブと、「すてて」の山なりのカーブが観察できます。

400_dyn

(4)PIT(ピッチベンド)について
 PIT(ピッチベンド)は音程です。この値が大きければ音程が高くなります。

 400氏のVSQファイルのPITをDYNと共に表示します、PITはDYNと極めて高い相関性をもって変化する特徴を有します。ただし、発音要素が短いときにはDYNは極めて大きな山なりカーブになるのに対して、PITは発音要素が短くても長くてもあまり変化せず、音節全体のカーブもゆるやかです。その代わり長い発音要素のときの正弦波状のカーブはDYNよりも振幅が大きいです。400氏のVSQファイルから感じるビブラートの主たる要素は、音程の周期的な変化で、従たる要素は音量の周期的な変化なのだと推定します。

400_pit

念押しでVSQファイルを直にエディタで見てみましたが、他に操作していたパラメータは見当たりませんでした。

 なお、MIKU_TALK の作成、及び400氏のVSQファイル解析にあたり、「日本語アクセントの概要」を参考とさせていただきました。

| | コメント (2) | トラックバック (0)

ぼかりす

 久しぶりに心踊るような技術が出てきました。まあ聞いてみてください。藤田咲さんが生で歌っているよと言われたら信じてしまいそうな出来ですが、これは「初音ミク」なんですよね。

さて、この「ぼかりす」ですが、2008年5月28日(水)に開催される「第75回音楽情報科学研究会」で研究成果として発表されるVocaListenerという技術だそうです。以下に表題と発表者を引用します。

(9) VocaListener: ユーザ歌唱を真似る歌声合成パラメータを自動推定するシステムの提案   
中野倫靖,後藤真孝(産総研)

 VocaListerner が何をやっているかは現時点では不明です。よって、さっそく後藤真孝さんの素性を調べてみました。とりあえず特許検索ということで、後藤さんの音関係の特許出願及び登録特許を列挙します。リンクを叩くとPDFが開きます。

特開2001-125562 音高推定方法及び装置

(57)【要約】
【課題】本発明は、入力音響信号に対してあるパート(メロディーやベース)の音高推定を可能にするために、混合音中で優勢な音高を推定することを目的としている。
【解決手段】本発明は、入力音響信号に対してマルチレート信号処理をおこなって瞬時周波数を計算し、瞬時周波数に関連した尺度に基づいて周波数成分の候補を抽出する。次に、2種類のバンドパスフィルタ(メロディーライン用とベースライン用)を適用し、それぞれの出力に基づいて、基本周波数(音高)の確率密度関数を求める。そして、マルチエージェントモデルを導入し、その確率密度関数の中で有望な各ピークの軌跡を異なるエージェントが追跡して、それぞれの信頼度を評価する。最後に、最も信頼度の高いエージェントが持つ優勢な基本周波数の軌跡を出力する。

特許3413634 音高推定方法及び装置(上記出願が権利化したもの)

特開2008-058753 音分析装置およびプログラム

(57)【要約】
【課題】 記憶する音モデルの個数が比較的少なくて済み、かつ、高い推定精度で基本周波数を推定できるようにする。
【解決手段】 音モデル補間処理5では、記憶装置に記憶された複数種類の音モデルに補間処理を施し、各音モデルの中間の基本周波数に対応した複数種類の音モデルを生成する。基本周波数の確率密度関数の推定41では、記憶された音モデルおよび補間処理により得られた音モデルを用いて、様々な基本周波数の音モデルの混合分布を構成し、この混合分布が入力音響信号の周波数成分の分布となるように、各音モデルに対する重み値を最適化し、最適化された各音モデルの重み値を音源の音の基本周波数の確率密度関数とする。

特開2008-058754 音分析装置およびプログラム

57)【要約】
【課題】 混合音を示す入力音響信号の周波数成分から各音の基本周波数を推定する際に、基本周波数の誤った推定が行われるのを防止する。
【解決手段】 周波数帯域の制限3では、入力音響信号から音源の音の基本周波数成分または高調波成分となる可能性のある周波数成分を抽出する。基本周波数の確率密度関数の推定41では、抽出された周波数成分が各々高調波構造を有し、異なる基本周波数に対応した音モデルの混合分布から生じたと考え、基本周波数の確率密度関数を推定する。音モデル変形処理5では、その際の誤推定の可能性を低減するための音モデルの変形を行う。

特開2008-058755 音分析装置およびプログラム

(57)【要約】
【課題】 EMアルゴリズムにより、入力音響信号から、鳴っている音の基本周波数を求める際に、楽器固有の事前知識を利用して、精度良く基本周波数を推定する。
【解決手段】 フォーム推定413では、EステップおよびMステップ411により各種の基本周波数に対応した重み値を逐次更新される過程において、音源構造データ413Fにより定義された制約条件を満たすように、重み値のピークの中から、発音されている可能性が高いと推定される音のものを選択する。事前分布付与414では、この選択したピークが強調されるように、各音モデルに対する重み値に事前分布を与える。

特開2008-058885 音高推定装置、音高推定方法およびプログラム

(57)【要約】
【課題】音高を高精度に推定する。
【解決手段】音響推定装置Dは、音響信号Vを複数の音モデルの混合分布としてモデル化したときの各音モデルの重み値ω[F]の分布である基本周波数の確率密度関数Pから音響信号Vの基本周波数F0を推定する装置である。関数推定部20は、重み値ω[F]を更新する単位処理を反復するEMアルゴリズムによって確率密度関数Pを推定する。重み値修正部22は、単位処理で算定された重み値ω[F]に現れる複数のピークのピーク値を増加させた修正値ωa[F]を、次回の単位処理で使用される重み値ω[F]として生成する。音高特定部40は、確率密度関数Pのピークに対応した基本周波数F0を特定する。

特開2008-058886 音高推定装置、音高推定方法およびプログラム

(57)【要約】
【課題】音高を高精度に推定する。
【解決手段】音響推定装置Dは、音響信号Vを複数の音モデルM[F]の混合分布としてモデル化したときの各音モデルM[F]の重み値ω[F]の分布である基本周波数の確率密度関数Pから音響信号Vの基本周波数F0を推定する装置である。重み値算定部23は、音モデルM[F]が音響信号Vの高調波構造を支持する程度を示す推定形状C[F]に基づいて重み値ω[F]を算定する。推定形状特定部21は、音響信号Vの振幅スペクトルSと音モデルM[F]と重み値ω[F]とに基づいて推定形状C[F]を特定する。類否解析部271は、音モデルM[F]とこの音モデルM[F]から特定された推定形状C[F]との類否を示す類否指標値R[F]を算定する。重み値修正部273は、重み値ω[F]のうち類否指標値R[F]が非類似を示す基本周波数Fの重み値ω[F]を低下させる。

 いずれの特許出願も音高(PIT)を高精度に推定するというもので、課題が共通しています。この中で、もっとも最初に出願された特開2001-125562(特願平11-305770)が「ぼかりす」に適用された発明ではないかと推定しました。以下に図5を引用します。人間の歌声を入力として、出力された melody line をボーカロイド2の音階に割り当てれば、かなり正確な音高が初音ミクで再現できるのではないでしょうか。

Jpa_2001125562_fig6

 しかし、「ぼかりす」は、音高(PIT)のみで出力しているにしては自然すぎ、更に幾つかの隠し技を入れているようにも思えます。詳しくは5月28日の有志の報告を待つことにしたいと思います。

 最初の特許を除く5件の特許は産業技術総合研究所とヤマハ株式会社の共同出願だったので、ちょっと驚いてしまいました。初音ミクのヒットの前から着実に活動していますね。この「ぼかりす」の仕掛け人も、恐らくヤマハ株式会社だったのでしょう。この5件の特許の出願日は初音ミク発売のおよそ1年前の2006年9月1日と9月4日で、共同発明者はいずれもヤマハ株式会社の藤島琢哉さんと有元慶太さんです。

追記:MiruSinger:歌を「歌って/聴いて/描いて」見る歌唱力向上支援インタフェース も何か関係するかもしれません。

論文はこちらです。

MiruSinger:歌を「歌って/聴いて/描いて」見る歌唱力向上支援インタフェース」。

 この論文には音高と共にビブラートを自動検出する技術が記載されており、著者のうち2人はVocaListernerと一致しています。よって、「ぼかりす」は MiruSinger と同様に音階と共にビブラートを検出して、VSQに反映させていると思われます。以下に論文の要点を引用します。

3 MiruSinger の実現方法
入力信号中で最も優勢な(パワーの大きい) 高調波構造を求める手法[4]混合音中で最も優勢な音高を推定する手法(PreFEst)[5]推定されたF0 軌跡の1 次差分の短時間フーリエ変換によってビブラートらしさを得る手法[3] を用いた。ただし、混合音からのF0 推定では、中高域で最も優勢な高調波構造を持つF0 がボーカルのF0 であると仮定した。

| | コメント (5) | トラックバック (1)

MIKU_TALK 使用コンテンツについて

MIKU_TALK を使用いただいているコンテンツを紹介します。

こちらは、宮沢賢治の「注文の多い料理店」の序章を喋らせているというもので、噂のMikuMikuDanceの3D画像と同期させています。流石です、MikuMikuDance の使いこなしテクニックをもう少し詳細に書いて欲しいかも・・・(笑)。

こちらは、「miku_talk012.plをexe化してGUIをつけてみた」のコンテンツです。mod_perl を使って GUI化して使いやすくしていただいています。これを見て、miku_talk20.pl を早く公開せねばと思いました。ちょっとソースコードを触ってマイナーなバグを潰してから公開しますのでお待ちください。

こちらは「初音ミクでゆっくりしていってね!!!」というコンテンツです。そういえば、自分も2chで有名な「吉野家コピペ」や「ここはひどいインターネッツですね」とかを喋らせてみたことがあります。何かミクに喋らせるのに適当なコピペがありましたらトライしてみてください。

| | コメント (0) | トラックバック (0)

ヤマハ株式会社・組込み信号処理ソフトウェア開発<研究・開発部門>

ヤマハ株式会社が組込み信号処理ソフトウェア開発者の求人を掛けています。
http://rikunabi-next.yahoo.co.jp/rnc/docs/cp_s01800.jsp?rqmt_id=0005554945

この求人の要旨を引用します。

仕事の内容    
高品位な事業・製品を創出するための信号処理技術の研究・開発

      
【具体的には】
●組込み信号処理ソフトウェア開発
●DSPアルゴリズム開発など

対象となる方
工学系・理学系大卒以上

      
【具体的には】
●いずれかの分野における業務(応用技術開発、製品開発、設計)経験をお持ちの方
組込みソフトウェア
デジタル信号処理(デジタルフィルタ・フーリエ変換など)
オーディオ・楽音信号処理技術
センサー情報処理
音声通信技術
超音波応用
※新しい技術の発想や発明に積極的で、特許としてまとめる能力をお持ちの方は、特に歓迎いたします。

仕事の内容が「信号処理技術」で、具体的には組込み信号処理等とすると、恐らくヤマハ MA-7シリーズの後継LSI(MA-9?) の開発ではないかと推定します。
http://smaf-yamaha.com/jp/what/soundchip_ma7.html

現在のMA-7の機能に加えて欲しい機能は、「VSQファイルを入力すると音声化する機能」「音声を入力するとVSQファイルに変換する機能」「メールの読上機能」「日本語音声の自動テキスト化」などです。VSQファイルの音声化機能を付けたら、MA-9 ではなく、LSI-VOCALOID2 と銘打って発売して欲しいと思いました。この求人に応募された方はご参考になさってください。

追記:ネットワーク常時接続の携帯電話が普及したならば、VSQファイルの音声化はLSI上の信号処理ではなく、WEB-APIを使っても可能ですね。ちょっと頭が固かったようです。

| | コメント (0) | トラックバック (0)

MIKU_TALK 0.2.0 ソース (形態素解析パート)

 MIKU_TALK Ver. 0.2.0 の形態素解析パート ActionScript 3.0 のコードを貼ります。Flex SDK 2.0 でコンパイル可能です。ただし"(アプリケーションID)"の部分は、各自 Yahoo にアプリケーションIDを申請の上で、そのID文字列を入力する必要があります。

Yahoo! 形態素解析サービスをWEBアプリケーションで使うときのサンプルとしてお使いください。

<?xml version="1.0"?>
<mx:Application xmlns:mx="http://www.adobe.com/2006/mxml"
creationComplete="init()">
<mx:Script>
  <![CDATA[
  import mx.controls.Alert;
  import flash.net.*;
//import flash.external.*;
  import mx.rpc.events.FaultEvent;
  import mx.rpc.events.ResultEvent;

  private var loader:URLLoader;
  default xml namespace = new Namespace("urn:yahoo:jp:jlp");

  private function init():void
  {
   write_sample();
  }

  private function request():void
  {
   yahoo_ma.text = "";

   if( sentence.text.length == 0 ) {
    Alert.show('自然文が入力されていません', 'Message');
    return;
   }
   if( 2000 <= sentence.text.length ) {
    Alert.show('自然文が2000文字を超えています'
    + sentence.text.length, 'Message');
    return;
   }

   var variables:Object = new Object();
   // variables.appid = "miku_talker";
   variables.sentence = sentence.text;
   yahoo_ma_service.send(variables);
  }

  private function delete_parenthesis():void
  {
   var work_sentence:String = "";
   var c:String = "";
   var isParenthesis:Number = 0;

   for(var i:Number=0; i<sentence.text.length; i++){
    c = sentence.text.charAt(i);
    if( c == "(" || c == "(" ) {
     isParenthesis++;
    } else {
     if( c == ")" || c == ")" ) {
      if( 0 < isParenthesis ) {
       isParenthesis--;
      }
     } else {
      if( isParenthesis == 0 ) {
       work_sentence += c;
      }
     }
    }
   }
   sentence.text = work_sentence;
  }

  private function setResponse(event:ResultEvent):void
  {
   var response:XML = yahoo_ma_service.lastResult as XML;
   var total_count:Number = response.ma_result.total_count;
   var filtered_count:Number = response.ma_result.filtered_count;

   for(var i:Number=0; i<total_count; i++){
    var surface:String   = response.ma_result.word_list.word[i].surface;
    var pos:String       = response.ma_result.word_list.word[i].pos;
    var reading:String   = response.ma_result.word_list.word[i].reading;
    var pronounce:String = reading;

    if( "0".charCodeAt(0) <= reading.charCodeAt(0)
    && reading.charCodeAt(0) <= "9".charCodeAt(0) ) {
     pronounce = pronounce_number(reading);
    } else {
     pronounce = pronounce_alphabet(reading);
    }
    if( pos == "助詞" ) {
     if( reading == "へ" ) {
      pronounce = "え";
     }
     if( reading == "は" ) {
      pronounce = "わ";
     }
    }
    if( pos == "名詞" ) {
     if( surface.charAt(0) == "・"
     ||  surface.charAt(0) == "…" ) {
      reading   = surface;
      pronounce = surface;
     }
    }
    pronounce = pronounce_tyouon(pronounce);
    yahoo_ma.text += surface + "\t"
        + pos       + ",,,,,,,"
        + reading   + ","
        + pronounce + "\n";
   }
  }

  private function pronounce_number(reading:String):String
  {
   var pronounce:String = "";
   var currentFigure:Number = reading.length;
   var pronounceFigure:Number = 1;

   if( currentFigure > 17 ) return "よめない";

   for(var i:Number = 0; i<reading.length; i++,currentFigure--) {
    if( reading.charAt(i) == "0" ) {
     if( reading.length == 1 ) pronounce += "ぜろ";
    }
    if( reading.charAt(i) == "1" ) {
     if( currentFigure % 4 == 1 ) pronounce += "いち";
     if( currentFigure % 4 == 0
     && 4 < currentFigure ) pronounce += "いっ";
    }
    if( reading.charAt(i) == "2" ) pronounce += "に";
    if( reading.charAt(i) == "3" ) pronounce += "さん";
    if( reading.charAt(i) == "4" ) pronounce += "よん";
    if( reading.charAt(i) == "5" ) pronounce += "ご";
    if( reading.charAt(i) == "6" ) pronounce += "ろく";
    if( reading.charAt(i) == "7" ) pronounce += "しち";
    if( reading.charAt(i) == "8" ) pronounce += "はち";
    if( reading.charAt(i) == "9" ) pronounce += "きゅう";

    if( reading.charAt(i) != "0" ) {
     if( currentFigure % 4 == 2 ) {
      pronounce += "じゅう";
      pronounceFigure = 1;
     }
     if( currentFigure % 4 == 3 ) {
      pronounce += "ひゃく";
      pronounceFigure = 1;
     }
     if( currentFigure % 4 == 0 ) {
      pronounce += "せん";
      pronounceFigure = 1;
     }
    }
    if( currentFigure ==  5 && pronounceFigure == 1 ) {
     pronounce += "まん";
     pronounceFigure = 0;
    }
    if( currentFigure ==  9 && pronounceFigure == 1 ) {
     pronounce += "おく";
     pronounceFigure = 0;
    }
    if( currentFigure == 13 && pronounceFigure == 1 ) {
     pronounce += "ちょう";
     pronounceFigure = 0;
    }
   }
   return pronounce;
  }
  private function pronounce_tyouon(pronounce_in:String):String
  {
   var pronounce:String = "";
   var a_gyou:String = "あかさたなはまやらわがざだばぱゃ";
   var i_gyou:String = "いきしちにひみりぎじぢびぴ";
   var u_gyou:String = "うくすつぬふむゆるぐずづぶぷゅ";
   var e_gyou:String = "えけせてねへめれげぜでべぺ";
   var o_gyou:String = "おこそとのほもよろをごぞどぼぽょ";

   if( pronounce_in.length==0 ) {
    return pronounce;
   }
   pronounce = pronounce_in.charAt(0);
   for(var i:Number = 1; i<pronounce_in.length; i++) {
    var c0:String = pronounce_in.charAt(i-1);
    var c1:String = pronounce_in.charAt(i);

    if((0 <= a_gyou.indexOf(c0,0) && c1 == "あ")
    || (0 <= i_gyou.indexOf(c0,0) && c1 == "い")
    || (0 <= u_gyou.indexOf(c0,0) && c1 == "う")
    || (0 <= u_gyou.indexOf(c0,0) && c1 == "お")
    || (0 <= e_gyou.indexOf(c0,0) && c1 == "い")
    || (0 <= e_gyou.indexOf(c0,0) && c1 == "え")
    || (0 <= o_gyou.indexOf(c0,0) && c1 == "う")
    || (0 <= o_gyou.indexOf(c0,0) && c1 == "お")) {
     pronounce += "ー";
    } else {
     pronounce += c1;
    }
   }
   return pronounce;
  }

  private function pronounce_alphabet(reading:String):String
  {
   var pronounce:String = "";

   for(var i:Number = 0; i<reading.length; i++) {
    var c:String = reading.charAt(i);
    var cOut:String = "";

    if( c == "A" || c=="A" || c=="a" || c=="a" ) cOut = "えい";
    if( c == "B" || c=="B" || c=="b" || c=="b" ) cOut = "びい";
    if( c == "C" || c=="C" || c=="c" || c=="c" ) cOut = "しい";
    if( c == "D" || c=="D" || c=="d" || c=="d" ) cOut = "でえ";
    if( c == "E" || c=="E" || c=="e" || c=="e" ) cOut = "いい";
    if( c == "F" || c=="F" || c=="f" || c=="f" ) cOut = "えふ";
    if( c == "G" || c=="G" || c=="g" || c=="g" ) cOut = "じい";
    if( c == "H" || c=="H" || c=="h" || c=="h" ) cOut = "えいち";
    if( c == "I" || c=="I" || c=="i" || c=="i" ) cOut = "あい";
    if( c == "J" || c=="J" || c=="j" || c=="j" ) cOut = "じぇい";
    if( c == "K" || c=="K" || c=="k" || c=="k" ) cOut = "けい";
    if( c == "L" || c=="L" || c=="l" || c=="l" ) cOut = "える";
    if( c == "M" || c=="M" || c=="m" || c=="m" ) cOut = "えむ";
    if( c == "N" || c=="N" || c=="n" || c=="n" ) cOut = "えぬ";
    if( c == "O" || c=="O" || c=="o" || c=="o" ) cOut = "おお";
    if( c == "P" || c=="P" || c=="p" || c=="p" ) cOut = "ぴい";
    if( c == "Q" || c=="Q" || c=="q" || c=="q" ) cOut = "きゅう";
    if( c == "R" || c=="R" || c=="r" || c=="r" ) cOut = "あある";
    if( c == "S" || c=="S" || c=="s" || c=="s" ) cOut = "えす";
    if( c == "T" || c=="T" || c=="t" || c=="t" ) cOut = "てい";
    if( c == "U" || c=="U" || c=="u" || c=="u" ) cOut = "ゆう";
    if( c == "V" || c=="V" || c=="v" || c=="v" ) cOut = "ぶい";
    if( c == "W" || c=="W" || c=="w" || c=="w" ) cOut = "だぶりゅ";
    if( c == "X" || c=="X" || c=="x" || c=="x" ) cOut = "えっくす";
    if( c == "Y" || c=="Y" || c=="y" || c=="y" ) cOut = "わい";
    if( c == "Z" || c=="Z" || c=="z" || c=="z" ) cOut = "ぜっと";
    if( c == "%" || c=="%" ) cOut = "ぱーせんと";
    if( c == "#" || c=="#" ) cOut = "しゃーぷ";
    if( c == "@" || c=="@" ) cOut = "あっと";
    if( c == "\\"|| c=="¥" ) cOut = "えん";
    if( c == "$" || c=="$" ) cOut = "どる";
    if( c == "&" || c=="&" ) cOut = "あんど";
    if( cOut == "" ) cOut = c;
    pronounce += cOut;
   }
   return pronounce;
  }

  private function error(event:FaultEvent):void
  {
   yahoo_ma.text = event.toString();
  }

  private function clear_sentence():void
  {
   sentence.text = "";
  }

  private function write_sample():void
  {
   sentence.text = "今日の天気は、一日中晴れ。";
  }

  private function clear_yahoo_ma():void
  {
   yahoo_ma.text = "";
  }

  private function submitCgi():void
  {
   if( yahoo_ma.text.length == 0 ) {
    Alert.show('形態素が入力されていません', 'Message');
    return;
   }
   var mylines:Number = 0;
   for(var i:Number = 0; i<yahoo_ma.text.length; i++) {
    var c:String = yahoo_ma.text.charAt(i);
    if( c == "\n" ) mylines++;
   }
   if( 1200 <= mylines ) {
    Alert.show('形態素が1200個を超えています', 'Message');
    return;
   }
   var myVars:URLVariables = new URLVariables();
   myVars.myText1 = yahoo_ma.text;
   myVars.debug   = "0";

   var myReq:URLRequest = new URLRequest();
   myReq.url = "../cgi-bin/miku_talk/miku_talk020.cgi";
   myReq.data = myVars;
   myReq.method = "POST";
   navigateToURL(myReq,"_top");
  }
]]>
</mx:Script>

<mx:HTTPService id="yahoo_ma_service"
  url="http://api.jlp.yahoo.co.jp/MAService/V1/parse?appid=(アプリケーションID)"
  method="POST" resultFormat="e4x"
  result="setResponse(event)"
  fault="error(event)">
</mx:HTTPService>

<mx:Panel title="自然文を元に形態素解析  MIKU_TALK Ver. 0.2.0"
width="100%" height="50%" id="main_panel" layout="vertical">
  <mx:HBox width="100%" height="85%">
   <mx:Label text="自然文"/>
   <mx:TextArea id="sentence" width="100%" height="100%" backgroundColor="#EEFFEE" wordWrap="true">
    <mx:text></mx:text>
   </mx:TextArea>
  </mx:HBox>
<mx:HBox width="100%" height="15%">
  <mx:Button label="形態素解析" click="request()"/>
  <mx:Button label="括弧削除" click="delete_parenthesis()"/>
  <mx:Button label="消去" click="clear_sentence()"/>
  <mx:Button label="例文" click="write_sample()"/>
</mx:HBox>
</mx:Panel>
<mx:Panel title="形態素を元にVSQ生成" width="100%" height="50%" id="sub_panel" layout="vertical">
  <mx:HBox width="100%" height="85%">
   <mx:Label text="形態素"/>
   <mx:TextArea id="yahoo_ma" width="100%" height="100%" backgroundColor="#EEFFEE" wordWrap="true">
    <mx:text></mx:text>
   </mx:TextArea>
  </mx:HBox>
   <mx:HBox width="100%" height="15%">
    <mx:Button label="VSQ生成" click="submitCgi()"/>
    <mx:Button label="消去" click="clear_yahoo_ma()"/>
   </mx:HBox>
</mx:Panel>
</mx:Application>

関数について解説します。

private function init():void
このswfファイルが起動したときに呼び出され、例文 "今日の天気は一日中晴れ" を自然文入力部分に設定しています。

private function request():void
形態素解析ボタンを押したとき、Yahoo! 形態素解析サービスで、自然文を形態素に解析します。

private function delete_parenthesis():void
括弧を削除します。

private function setResponse(event:ResultEvent):void
形態素解析サービスの処理の後に呼び出され、XML形式をCSV形式に変換します。

private function pronounce_number(reading:String):String
数字を平仮名で読みます。

private function pronounce_tyouon(pronounce_in:String):String
長音で発音する平仮名文字列を検出します。
(ぼおかろいど→ぼーかろいど)

private function pronounce_alphabet(reading:String):String
アルファベットを平仮名で読みます。

private function error(event:FaultEvent):void
形態素解析のエラーのときの処理です。

private function clear_sentence():void
自然文入力部をクリアします。

private function write_sample():void
自然文入力部に例文を入力します。

private function clear_yahoo_ma():void
形態素解析部をクリアします。

private function submitCgi():void
形態素解析部をCGIに渡します。

| | コメント (0) | トラックバック (0)

ソフトウエア実験室(MIKU_TALK)の移転について

今、sp-land のサーバーが完全にダウンしていますね。
今後の MIKU_TALK の安定運用の為、「和泉聡のソフトウエア実験室」は、本格的に infoseek に移転することにしました。

http://akira-izumi.hp.infoseek.co.jp/

こちらのサイトでもMIKU_TALK は今まで通りにお使いいただけますし、@nifty にもミラーサイトを立ち上げる予定です。但し、@nifty にミラーを作るのはちょっとだけ面倒です。

そのあたりの技術解説を含めて当該ブログに記載してゆきます。

| | コメント (0) | トラックバック (0)

ソフトウエア実験室のミラーサイト開設

今までは、sp-land にソフトウエア実験室を開設していたのですが、ちょっとコンテンツが重くてサーバ管理の方に申し訳なかったですね。

和泉聡のソフトウエア実験室 @sp-land
http://akiraizumi.sv1.sp-land.net/

そういう訳で、infoseek にソフトウエア実験室のミラーサイトを開設することにしました。こちらは割と軽く動いてくれると思います。今後はこちらをメインにバージョンアップする予定です。

和泉聡のソフトウエア実験室 @ infoseek
http://akira-izumi.hp.infoseek.co.jp/

| | コメント (0) | トラックバック (0)

On line Vocaloid

あの「初音ミク」の「VOCALOID」オンライン版が本邦初公開
http://bb.watch.impress.co.jp/blog/archives/2008/04/macvocaloid.html

これは面白い取り組みですね。
 PCアプリケーションとして実装したならば、OSの縛りを脱却するのは難しいです。開発工数はOS数に比例して増加します。しかし、販売本数はWindows が圧倒的で、Mac OS X ユーザーはごく少数(現在は3~5%)ですので、Macintosh の開発費用を回収するのは難しく、よって営業的な判断により Windows 版のみを開発するという場合が多いです。
 しかし、WEBアプリケーションとして実装したならば、OSの縛りを超えてマルチOS対応するのは、それほど難しいことではありませんし、OS数に比例して開発工数が増加することはありません。よって、開発工数を削減し、かつミュージシャンやクリエータの比率が高い Mac OS X ユーザーを取り込むには、On line Vocaloid というアプローチが良いと思われます。
 更に、バグ対応が迅速にできるとか、規約違反の○×△な音声ファイルを作成しているユーザーをすぐさま特定できるとかいう効果もあります。
 余談ですが、自分も MIKU_TALK WEBアプリケーションで、「卑猥な言葉を喋らせようとするとミクが怒る(ミクの怒った顔が表示される)」機能を付けようかと思ったのですが、かえって、「怒った顔が見たくてヒワイな言葉を入力する」ユーザーが出てきて、火に油を注ぐような気がしましたので止めました。(笑) Yamaha さんも、On line Vocaloid に同様に機能を実装される場合にはご一考ください。

追記:
昨年度10月の自分のブログで、"VOCALOID WEB-API" について記載していましたね。どこのブログで見つけたのかはもう探れませんでした。リンクを貼っておけばよかったですね。
http://akira-izumi.cocolog-nifty.com/patent/2007/10/vocaloid_8b20.html

| | コメント (0) | トラックバック (0)

Yahoo!の形態素解析の動作変更?!

 今日、miku_talk の形態素解析ボタンが動作しないので、ちょっと焦りました。
 いままで、自然文を送信するのに POSTリクエストを使っていたのですが、Yahoo側の動作が変わり、POSTリクエストは受け付けなくなったようですね。仕様とおりに、自然文をGETリクエストで送信すると、うまく変換できるようになりました。やはりソフトウエアは仕様書通りに作るのが大切のようです。
 POST リクエストを使った理由は、GETリクエストよりも大量データが問題なく処理できそうという予測および、参考にしたサンプルコードがPOSTリクエストを使っていたことによります。基本を疎かにして、不具合を出してしまいました。ちょっと反省です。

| | コメント (0) | トラックバック (0)

人力ボカロ支援ツール

噂の人力ボカロ支援ツールのガイダンスビデオを見てみました。



いや凄いですね。個人が作成するフリーソフトで、これだけのことができるのは大したものです。

なお、ビデオ中の音素ファイルの名称が「釘宮理恵さま.wav」とありますが、このソフトは自分が作ったものではありません。(笑)

| | コメント (0) | トラックバック (0)

初音ミクに喋らせてみた(0.2.0版)

初音ミクに喋らせるためのWEBアプリケーション MIKU_TALK Ver. 0.2.0 を作成いたしました。以下の URL から利用できます。

http://akiraizumi.sv1.sp-land.net/yahoo_ma20/yahoo_ma.html

MIKU_TALK Ver.0.2.0に於ける主な追加機能は以下のものです。

  • 括弧の削除機能

    形態素解析前に括弧を削除することが可能です。青空文庫は、漢字の直後に読み仮名を括弧付きで付加しており、同じ漢字を二重に発音する恐れがある為です。また、法律の条文などは付加的な説明文を括弧付きで付加していますが、冗長な場合も多い為です。

  • 長音の処理

    形態素解析パートにて、同一母音の連続又は特定母音を長音に変換する機能を付加しました。具体的には「ボオカロイド」は「ボーカロイド」に、「はつめい」は「はつめー」に変換されます。これにより、日本人の通常の発音に近づけることができました。

  • 品詞毎の調整

    VSQ生成パートにて、品詞が名詞ならば音量(DYN)を80に、形容詞/形容動詞/接頭詞/感動詞/接頭辞/副詞ならば音量(DYN)を72にして音程(PIT)を高めに設定し、それ以外の品詞ならば、音量(DYN)を64にして音程(PIT)を低めに設定いたしました。これにより、品詞の重要度に応じて音量・音程を調整している様子を表現しました。

  • 子音毎のベロシティ調整

    カ行とサ行と「つ」はベロシティ(VEL)を大きく(子音を短く)、ラ行はベロシティ(VEL)を小さく(子音を長く)発音するように致しました。これは、「初音ミク」の音素テーブルはカ行サ行「つ」の子音が強く、ラ行の子音は弱いという癖があり、その癖を矯正して自然に発音させるためです。よって、他のVOCALOID製品では異なったチューニングが必要と思われます。

  • 単語の区切り

    単語を連続で5~7音素連続して発音すると少しだけ時間間隔を空けます。日本語は5音素または7音素で区切って発音される事が多いためです。

    また、句読点「、」「。」で時間間隔を空けると同時に息継ぎをおこない、句読点の直前の単語では音程を下げます。これにより文章の構造を理解して喋る様子を表現しました。

以下が MIKU_TALK Ver. 0.2.0 のサンプルです。


ただいま留守にしております。ご用件のある方はピーッという音の後にメッセージを入れてください。

特許法第2条

蜘蛛の糸 芥川龍之介

雨ニモマケズ 宮沢賢治

| | コメント (0) | トラックバック (0)

剣持氏のセミナー講演

剣持氏がデジタルコンテンツ協会のセミナーで講演されたそうです。この記事をもとに幾つかコメントします。

「Mac版まだ?」「自分の声で歌えない?」――VOCALOID、よくある質問
http://www.itmedia.co.jp/news/articles/0803/17/news108.html

最初の図面が、かつて当ブログで引用したVOCALOID概念図そのものでした。考えて見れば剣持氏が初音ミク発売直前に学会発表したものですから当然ですね。
この記事では、ユーザーの要望が幾つか述べられています。

◆Mac版は?
 日本における MacOS Xのシェア(数%)を考えると、そんなところに開発リソースを割きたくないというのが商業的な判断なのでしょうね。でも、開発者的にはちょっとそそられる課題とおもいます。
 もしYAMAHAさんが本当にMac版VOCALOID2を開発されるならば、MOSAあたりに連絡をとると宜しいかとおもいます。恐らく日本最高の Mac OS X 使いを紹介いただけるかと思います。
http://www.mosa.gr.jp/

◆自分の声で音声合成
 剣持さんは「できません。」と答えているけれど、そのうちに出来るようになると思います。音声から本人の気道や声帯などを算出し、その気道や声帯から発生される音をシミュレーション出力することで「誰でもボーカロイド」が可能でしょう。但し、研究レベルならばともかく、商業的に成功するような品質を得るにはなかなか難しいかもしれません。

◆読み上げソフト・・・・
 これには思わずニヤニヤしてしまいました。フリーソフト作者のお遊びレベル以上にはなりませんよという意味なのでしょうね。

◆ゲーム機や携帯電話への搭載
 これは是非とも載せて欲しいですね。「こんどの携帯電話にはボーカロイドが載ってて歌ったりメール喋ったりするんだって~」なんてことになると、今の携帯電話を買い換えたくなるに違いありませんから。

| | コメント (2) | トラックバック (0)

wavtone で耳コピ

waveTone とは、あっきーさんが作成された耳コピー用のスペクトルアナライザーです。音声ファイルを解析し、音階ごとの音量のグラフをピアノロール形式で表示することができます。(Readme.txt より引用)

配布元URLはこちらです。
http://user.media.nagoya-u.ac.jp/people/h054072b/

これを用いることで、miku_talk のブラッシュアップができないかと考え てみました。
まず、リファレンス音声ファイル「今日の天気は、一日中晴れ」の音声ファイルを作成して、waveTone にドラッグ&ドロップしました。

Kyouno_tenki_ha

上の画面が解析画面です。ただし、倍音も同時に表示されているので判りにくいものになっています。そこで、倍音を除去して見やすい画面にします。

Kyouno_tenki_ha_01

同時に、どのタイミングで何が発音されていたかを表示しています。

この文章の形態素解析の結果は以下です。

今日    名詞,,,,,,,きょう,きょー
の    助詞,,,,,,,の,の
天気    名詞,,,,,,,てんき,てんき
は    助詞,,,,,,,は,わ
、    特殊,,,,,,,、,、
一日中    副詞,,,,,,,いちにちじゅう,いちにちじゅー
晴れ    名詞,,,,,,,はれ,はれ
。    特殊,,,,,,,。,。

ここから読み取れる特徴は以下のものです。

(1)「今日の天気は、」と、「一日中晴れ」でそれぞれ山なりの音階になっています。つまり、読点「、」と句点「。」で区切られた直後では音階が上がり、区切られる直前の単語では音階が下がります。文頭および文末を明示する為です。

(2)語中では次第に音階が下がってゆき、読点や句点の場所でふたたび音階が上がります。発音中に次第に音階が下がるのは人間の生理的な現象で、読点や句点で音階が上がるのは、息継ぎがおこなわれるためです。

(3)「今日」「天気」など、名詞は助詞と比べて強く発音されています。文章中で重要性が高いためと思われます。

もっと正確には、アクセントなどを付与しないといけないのですが、とりあえず現状は(1)(2)(3)のみで MIKU_TALK Ver 0.2.0 を試作してみました。

「kyouno_tenki_ha.mp3」をダウンロード

真面目に単語のアクセントを付与しないといけませんね。なんとなく関西弁風になってしまいます。

| | コメント (0) | トラックバック (0)

数字の日本語読み部分

google-code-prettify のテストを兼ねて、MIKU_TALK Ver. 0.1.8 の形態素解析パートで実装した「数字読み」の ActionScript 3.0 のコードを貼ります。

reading (読み)に数字が入っておりますので、各桁の数字(reading.charAt(i))を「いち」~「きゅう」と発音し(pronounce)、桁数(currentFigure)に対応した読み「おく」~「じゅう」の発音 (pronounce) をしています。

private function 
pronounce_number(reading:String):String
{
 var pronounce:String = "";
 var currentFigure:Number = reading.length;
 var pronounceFigure:Number = 1;

 if( currentFigure > 17 ) return "よめない";
 
 for(var i:Number=0; i<reading.length;
                          i++,currentFigure--) {

  if(reading.charAt(i) == "0") {
   if( reading.length == 1 ) pronounce += "ぜろ";
  }
  if(reading.charAt(i) == "1") {
   if(currentFigure % 4 == 1) 
     pronounce += "いち";
   if(currentFigure % 4 == 0 && 4 < currentFigure)
     pronounce += "いっ";
  }
  if(reading.charAt(i) == "2") pronounce += "に";
  if(reading.charAt(i) == "3") pronounce += "さん";
  if(reading.charAt(i) == "4") pronounce += "よん";
  if(reading.charAt(i) == "5") pronounce += "ご";
  if(reading.charAt(i) == "6") pronounce += "ろく";
  if(reading.charAt(i) == "7") pronounce += "しち";
  if(reading.charAt(i) == "8") pronounce += "はち";
  if(reading.charAt(i) == "9") pronounce += "きゅう";

  if( reading.charAt(i) != "0" ) {
   if( currentFigure % 4 == 2 ) {
    pronounce += "じゅう";
    pronounceFigure = 1;
   }
   if( currentFigure % 4 == 3 ) {
    pronounce += "ひゃく";
    pronounceFigure = 1;
   }
   if( currentFigure % 4 == 0 ) {
    pronounce += "せん";
    pronounceFigure = 1;
   }
  }
  if(currentFigure == 5 && pronounceFigure == 1) {
   pronounce += "まん";
   pronounceFigure = 0;
  }
  if(currentFigure == 9 && pronounceFigure == 1) {
   pronounce += "おく";
   pronounceFigure = 0;
  }
  if(currentFigure == 13 && pronounceFigure == 1) {
   pronounce += "ちょう";
   pronounceFigure = 0;
  }
 }
 return pronounce;
}

ソースコードがいまいち洗練されていないのは、これが ActionScript の処女作で、言語仕様がよくわかっていないためです。やっぱり参考書籍(以下参照)を買わなきゃダメかな。

| | コメント (0)

初音ミクに喋らせてみた(0.1.8版)

初音ミク用VSQファイル自動生成ソフトウエア MIKU_TALK Ver. 0.1.8 をWEBアプリケーション化いたしました。SP-LANDの「和泉聡のソフトウエア実験室」に設置してあります。

和泉聡のソフトウエア実験室
http://akiraizumi.sv1.sp-land.net/index.html

初音ミクは、極めて自然な高品質の歌唱音声を合成します。しかし、文章を喋ることは主目的ではないため、自然に喋らせるのは初音ミク単体ではかなり困難です。MIKU_TALK は自然文を初音ミクに喋らせるための前処理をおこない、初音ミクに喋らせることを容易とするソフトウエアです。

MIKU_TALK Ver. 0.1.8 はWEBアプリケーションですので、FLASH PLAYER 9 がインストールされているWindows環境ならば動作します。よって、複雑な ActivePerl / Mecab / Mecab-perl-binding 等のインストールを行わずとも MIKU_TALK が使用可能となりました。

今回の変更/追加仕様は以下の点です。

・自然文から形態素解析をおこなう処理と、形態素解析の結果からVSQを生成する処理を分離した。これにより、形態素解析のエラーを修正できるようになった。
・形態素解析エンジンとして Yahoo! 日本語形態素解析WEBサービスを使用するよう変更した。これにより解析精度がかなり向上した。
・数字/アルファベット及び一部の特殊記号(%$#&@)を読ませる機能を付加した。
・アクセントをピッチベンドで実現し、より自然なアクセントとした。
・括弧をnote を2段上げて表現し、会話の中と地の文章を音声のみで区別可能とした。

MIKU_TALK の解説文書とソースコードも、近日中に SP-LAND にて公開する予定です。


追記:助詞の「は」の読みを「わ」に、助詞の「へ」の読みを「え」に変換する処理がうまく働いていなかったので修正しました。

| | コメント (5) | トラックバック (0)

鏡音リンの商標登録出願

「鏡音リン・鏡音レン」の商標登録出願がやっと出願公開されました。今日、IPDL(特許電子図書館)を検索したらヒットしました。

リンとレンは別個に出願し、かつ称呼は「考えられる限り」多くにしたのですね。個人的には、指定区分 07 指定商品 ロードローラー 類似群 09A03 が無かったのは残念です。(笑)

(210) 【出願番号】 商願2007-116456
(220) 【出願日】 平成19年(2007)11月5日
  【先願権発生日】 平成19年(2007)11月5日
  【最終処分日】
  【最終処分種別】  
  【出願種別】  

  【商標(検索用)】 鏡音リン
(541) 【標準文字商標】 鏡音リン
(561) 【称呼】 カガミネリン,カガミオトリン,キョーオンリン,カガミネ,カガミオト,キョーオン,リン
(531) 【ウィーン図形分類】

(731) 【出願人】
  【氏名又は名称】 クリプトン・フューチャー・メディア株式会社

  【類似群】 05D01 09A01 09D01 09E21 09E26 09G53 19B33 24A01 24B02 24C01 24D01 24E01 25B02 26A01 26D01 41E01 41E02 41E03 41E04 41H01 41J01 41K01 41K02 41M01 41M06 41M08 41Z99 42G01 42N01 42N02 42N03 42P01 42P02 42P03 42Q01 42Q02 42Q03 42Q99 42R02 42R03 42X04 42X11 42X14 42X31
  【国際分類版表示】 第9版
(500) 【区分数】
(511) (512) 【商品及び役務の区分並びに指定商品又は指定役務】
移 動体電話による通信を用いてダウンロードされる移動体電話機の着信用の音楽,録画済みビデオディスク及びビデオテープ,自動販売機,駐車場用硬貨作動式 ゲート,作業記録機,写真複写機,手動計算機,製図用又は図案用の機械器具,タイムスタンプ,タイムレコーダー,電気計算機,パンチカードシステム機械, 票数計算機,ビリングマシン,郵便切手のはり付けチェック装置,ウエイトベルト,レギュレーター,家庭用テレビゲームおもちゃ,電気溶接装置,メトロノー ム,携帯用液晶画面ゲームおもちゃ用のプログラムを記憶させた電子回路及びCD―ROM,電子楽器用自動伴奏プログラムを記憶させた電子回路及び CD―ROM,電子出版物
28 スキーワックス,遊園地用機械器具(業務用テレビゲーム機を除く。),愛玩動物用おもちゃ,おもちゃ,人形,遊戯用器具,ビリヤード用具,運動用具,釣り具,昆虫採集用具
41 ゲー ム機械器具を備えた遊戯場・遊園地・その他の娯楽施設の提供,映画・演芸・演劇・音楽又は教育研修のための施設の提供,電子計算機端末による通信を用いて 行うゲーム又はゲームに関する映像の提供,ボウリング場・その他の運動施設の提供,レコード又は録音済み磁気テープの貸与,録画済み磁気テープの貸与,お もちゃの貸与,遊園地用機械器具の貸与,スロットマシンの貸与,遊戯用器具の貸与,映画・演芸・演劇又は音楽の演奏の興行の企画又は運営,映画の上映・制 作又は配給,演芸の上演,演劇の演出又は上演,音楽の演奏,放送番組の制作,音響用又は映像用のスタジオの提供,映写機及びその附属品の貸与,映写フィル ムの貸与,移動体電話による通信を用いて行うゲームの提供
42 イ ンターネット・電子メールその他の通信ネットワークを用いた電子計算機用プログラムの提供,移動体電話による電子計算機用プログラムの提供,気象情報の提 供,建築物の設計,測量,地質の調査,機械・装置若しくは器具(これらの部品を含む。)又はこれらの機械等により構成される設備の設計,デザインの考案, 電子計算機のプログラムの設計・作成又は保守,電子計算機・自動車その他その用途に応じて的確な操作をするためには高度の専門的な知識・技術又は経験を必 要とする機械の性能・操作方法等に関する紹介及び説明,医薬品・化粧品又は食品の試験・検査又は研究,建築又は都市計画に関する研究,公害の防止に関する 試験又は研究,電気に関する試験又は研究,土木に関する試験又は研究,農業・畜産又は水産に関する試験・検査又は研究,機械器具に関する試験又は研究,著 作権の利用に関する契約の代理又は媒介,社会保険に関する手続きの代理,計測器の貸与,電子計算機の貸与,電子計算機用プログラムの提供,理化学機械器具 の貸与,製図用具の貸与

...

(210) 【出願番号】 商願2007-116457
(220) 【出願日】 平成19年(2007)11月5日
  【先願権発生日】 平成19年(2007)11月5日
  【最終処分日】
  【最終処分種別】  
  【出願種別】  

  【商標(検索用)】 鏡音レン
(541) 【標準文字商標】 鏡音レン
(561) 【称呼】 カガミネレン,カガミオトレン,キョーオンレン,カガミネ,カガミオト,キョーオン,レン
(531) 【ウィーン図形分類】

(731) 【出願人】
  【氏名又は名称】 クリプトン・フューチャー・メディア株式会社

  【類似群】 05D01 09A01 09D01 09E21 09E26 09G53 19B33 24A01 24B02 24C01 24D01 24E01 25B02 26A01 26D01 41E01 41E02 41E03 41E04 41H01 41J01 41K01 41K02 41M01 41M06 41M08 41Z99 42G01 42N01 42N02 42N03 42P01 42P02 42P03 42Q01 42Q02 42Q03 42Q99 42R02 42R03 42X04 42X11 42X14 42X31
  【国際分類版表示】 第9版
(500) 【区分数】
(511) (512) 【商品及び役務の区分並びに指定商品又は指定役務】
移 動体電話による通信を用いてダウンロードされる移動体電話機の着信用の音楽,録画済みビデオディスク及びビデオテープ,自動販売機,駐車場用硬貨作動式 ゲート,作業記録機,写真複写機,手動計算機,製図用又は図案用の機械器具,タイムスタンプ,タイムレコーダー,電気計算機,パンチカードシステム機械, 票数計算機,ビリングマシン,郵便切手のはり付けチェック装置,ウエイトベルト,レギュレーター,家庭用テレビゲームおもちゃ,電気溶接装置,メトロノー ム,携帯用液晶画面ゲームおもちゃ用のプログラムを記憶させた電子回路及びCD―ROM,電子楽器用自動伴奏プログラムを記憶させた電子回路及び CD―ROM,電子出版物
28 スキーワックス,遊園地用機械器具(業務用テレビゲーム機を除く。),愛玩動物用おもちゃ,おもちゃ,人形,遊戯用器具,ビリヤード用具,運動用具,釣り具,昆虫採集用具
41 ゲー ム機械器具を備えた遊戯場・遊園地・その他の娯楽施設の提供,映画・演芸・演劇・音楽又は教育研修のための施設の提供,電子計算機端末による通信を用いて 行うゲーム又はゲームに関する映像の提供,ボウリング場・その他の運動施設の提供,レコード又は録音済み磁気テープの貸与,録画済み磁気テープの貸与,お もちゃの貸与,遊園地用機械器具の貸与,スロットマシンの貸与,遊戯用器具の貸与,映画・演芸・演劇又は音楽の演奏の興行の企画又は運営,映画の上映・制 作又は配給,演芸の上演,演劇の演出又は上演,音楽の演奏,放送番組の制作,音響用又は映像用のスタジオの提供,映写機及びその附属品の貸与,映写フィル ムの貸与,移動体電話による通信を用いて行うゲームの提供
42 イ ンターネット・電子メールその他の通信ネットワークを用いた電子計算機用プログラムの提供,移動体電話による電子計算機用プログラムの提供,気象情報の提 供,建築物の設計,測量,地質の調査,機械・装置若しくは器具(これらの部品を含む。)又はこれらの機械等により構成される設備の設計,デザインの考案, 電子計算機のプログラムの設計・作成又は保守,電子計算機・自動車その他その用途に応じて的確な操作をするためには高度の専門的な知識・技術又は経験を必 要とする機械の性能・操作方法等に関する紹介及び説明,医薬品・化粧品又は食品の試験・検査又は研究,建築又は都市計画に関する研究,公害の防止に関する 試験又は研究,電気に関する試験又は研究,土木に関する試験又は研究,農業・畜産又は水産に関する試験・検査又は研究,機械器具に関する試験又は研究,著 作権の利用に関する契約の代理又は媒介,社会保険に関する手続きの代理,計測器の貸与,電子計算機の貸与,電子計算機用プログラムの提供,理化学機械器具 の貸与,製図用具の貸与

| | コメント (0) | トラックバック (0)

他言語と初音ミクについて

こういう記事を見つけました。

初音ミクはエスペラントで歌えるか (Erimitejo より)

この記事が書かれたのは2007年9月15日です。初音ミクが発売されてわずか2週間で初音ミクと形態素解析について考察され、そして他言語に応用できるかと示唆されているのは流石とおもいます。

エスペラント語とは、世界共通言語として設計された人工言語のうち、もっとも成功しているものの一つです。設計者のザメンホフは、最初はラテン語を世界共通言語として考えていたが、ラテン語を実際に学ぶと難しいことに気づいたために、ラテン語をベースにスラブ系言語を取り入れて、独自の言語体系を構築したものです。

自分は、エスペラント語もさることならが、イタリア語・スペイン語などロマンス諸語ならば、初音ミクはかなり上手く歌えるのではと思います。

そういえば、初音ミク関連の主要開発者のひとりであるジョルディ・ボナタさんはスペインのボンベフラウ・ファブラ大学(UPF というそうです)の方ですね。Miku にスペイン民謡とか歌わせておられるのではないかと想像しています。

El Grup de Tecnologia Musical desenvolupa Vocaloid, un sintetitzador de veu cantada
http://www.upf.edu/cms/cms/grec/en/0304/1211.html

これは VOCALOID の最初の技術発表の頃ですね。

Universitat Pompeu Fabra’s research in Voice Processing
results into YAMAHA’s virtual singer software VOCALOID

http://www.iua.upf.es/mtg/notas_prensa/Vocaloid.htm

The European ICT Prize : Vocaloid
http://www.ict-prize.org/nominees/detail.html?id=309_330

上記2件は、MEIKO など VOCALOID 商品が発売されていた頃の記事とおもいます。

September 20 2007 :: Success of Vocaloid 2 in Japan
http://mtg.upf.edu/pages/news/single?id=76

初音ミクが日本で成功したという記事が、写真つきで紹介されています。

| | コメント (0) | トラックバック (0)

MecabとYahoo!の形態素解析の比較

Yahoo!の形態素解析を用いた miku_talk も試作してみました。Mecab と形態素解析の性能を比較するためです。速度的にはどちらでも十分に速くて実用的ですが、形態素解析にはそれぞれ一長一短あります。

今回の御題は宮沢賢治の「風の又三郎」です。青空文庫 のテキストを利用させていただきましたので、ここに感謝の意を表します。

谷川の岸に小さな学校がありました。
教室はたった一つでしたが生徒は三年生がないだけで、あとは一年から六年までみんなありました。運動場もテニスコートのくらいでしたが、すぐうしろは栗の木のあるきれいな草の山でしたし、運動場のすみにはごぼごぼつめたい水を噴く岩穴もあったのです。さわやかな九月一日の朝でした。青ぞらで風がどうと鳴り、日光は運動場いっぱいでした。黒い雪袴をはいた二人の一年生の子がどてをまわって運動場にはいって来て、まだほかにだれも来ていないのを見て、「ほう、おら一等だぞ。一等だぞ。」とかわるがわる叫びながら大よろこびで門をはいって来たのでしたが、ちょっと教室の中を見ますと、二人ともまるでびっくりして棒立ちになり、それから顔を見合わせてぶるぶるふるえましたが、ひとりはとうとう泣き出してしまいました。というわけは、そのしんとした朝の教室のなかにどこから来たのか、まるで顔も知らないおかしな赤い髪の子供がひとり、いちばん前の机にちゃんとすわっていたのです。そしてその机といったらまったくこの泣いた子の自分の机だったのです。

宮沢賢治 「風の又三郎」より

◆Mecab版 「kazeno_matasaburou.mp3」をダウンロード

1から9までの数字をちゃんと読めるが、10以上の数字を読むことはできません。
また、正確に文章を形態素に落としてくれる場合があるかと思えば、ときどきとんでもない読みをします。恐らく辞書の問題とはおもいます。
前回のブログの朗読のときでも、「初音みく」を「ハツオトミク」と読むのはまだしも、「設計者」を「せっけいもの」と読むのは失礼にあたるので、ちょっとまずいですね(笑)。
Mecabはユーザー辞書の定義ができるので、今度トライしてみたいとおもいます。

◆Yahoo!形態素解析版 「y_kazeno_matasaburou.mp3」をダウンロード

数字をまともに読まずに無視しますが、それ以外は正確に文章を形態素に落としてくれます。
Yahoo!形態素解析のいちばんの問題点は「使用者それぞれがアプリケーションIDを登録しなければならない」点です。Yahoo!のWEB-APIの利用許諾には、アプリケーションIDは一般に公開しないように記載されています。
ユーザーにそんな登録のための労力を強いるというのは、アプリケーションの使い勝手を極めて損なうものですので、リリース用アプリケーションに用いるのはためらってしまいます。

| | コメント (2) | トラックバック (1)

剣持氏インタビュー

DTMマガジン1月号増刊 「the VOCALOID CV01初音ミク」に掲載された、ヤマハ株式会社の剣持氏インタビューについて調べてみました。

◆足りない音階はピッチ変更することについて

剣持 ピッチの数は12音階全部を録るのが理想は理想なのかもしれませんが、録音に時間をかけすぎるとシンガーさんの声が変わったりしますから、実際は12音階すべては録らないようになっています。足りない音階は合成する際に内部的にピッチを変えて出力します。

(the VOCALOID CV01 初音ミク 37頁より)

12音階全てのデータを持たずに、内部的に変換を掛けることにより、シンガーの録音時間を短縮することにより声の変化を最小化するという効果が生まれますが、元々はVOCALOIDの音声データベースを圧縮することが目的だったようです。特開2005-234337「音声合成装置、音声合成方法、及び音声合成プログラム」が対応する特許出願と思われます。

【課題】 ハードウェア資源に大きな制約が課されている環境下においても、様々な種類の声質の合成音声を生成することができる音声合成装置等を提供する。
【解決手段】 1種類の音韻データを備えた音声合成装置100に声質変更部250及び声質データベース260を設ける。声質変更部250は、テキスト解析部220から供給される声質データ番号を検索キーとして声質データベース260を検索し、声質パラメータを取得する。声質変更部250は、取得した声質パラメータに基づいて、音韻データ取得部230によって取得される音韻データに示される各音韻の声質を変更する。

(特開2005-234337より)

◆音素を自然に変化させることについて

剣持 VOCALOID2では、これら素片同士の「伸ばし音区間」で要素を補完することにより、接続部で原理的に「音色の突然の変化」が発生しないようにしているんです。

(the VOCALOID CV01 初音ミク 37頁より)

音声素片の接続部での「音色の突然の変化」がおきないようにするには、スペクトル領域での調整をおこなっている、特開2003-255998「歌唱合成方法と装置及び記録媒体」が対応する特許出願と思われます。

【課題】 自然な 歌唱音声又は高品質の歌唱音声を合成する。
【解決手段】 音素又は音素連鎖からなる音声素片に対応する音声波形を周波数分析して周波数スペクトル(A)を検出する。周波数スペクトル(A)上でP1等の局所的ピークを検知し、これらのピークを含むR1等のスペクトル分布領域を指定する。各スペクトル分布領域毎に、振幅スペクトル分布を周波数軸に関して表わす振幅スペクトルデータと、位相スペクトル分布を周波数軸に関して表わす位相スペクトルデータとを生成する。各スペクトル分布領域の振幅スペクトル分布を入力音符ピッチに応じて周波数軸上で(B)の様に移動すべく振幅スペクトルデータを修正し、この修正に対応して位相スペクトルデータを修正する。所望の音色 に対応するスペクトル包絡に沿うようにスペクトル強度を調整する。修正された振幅及び位相スペクトルデータを時間領域の合成音声信号に変換する。

(特開2003-255998より)

◆所望のピッチに合わせて素片を変化させることについて

剣持 そして「こういったピッチで動く」っていうのだけ決まったら、それに合わせて他の全てのピッチが変動しますね。隣り合った素片同士は、波形自体もきれいにつながらなければならないので、・・・

(the VOCALOID CV01 初音ミク 37頁より)

ピッチに適合して音素の繋がりを調整する関する発明は、特開2002-202790「歌唱合成装置」 が対応する特許出願と思われます。発明者は、劔持秀紀さん、ザビエル・セラさんとジョルディ・ボナタさんです。

【課題】 高品質な歌声を合成する。
【解決手段】 スペクトルモデル合成(SMS)分析合成法において、音素または2つ以上の音素連鎖についてSMS分析を行いデータベース10を作成し、合成時に必要な音素または音素連鎖のSMSデータを接続し合成することで歌声を得る。前記データベース10には、同じ音素あるいは音素連鎖につき、異なるピッチ、ダイナミクス、テンポごとに別個の素片データを記憶する。調和成分調整手段22、非調和成分調整手段23で、読み出した素片データの調和成分および非調和成分を目的のピッチに合うように調整し、継続時間調整手段24で目的のテンポに合うように音素または音素連鎖の長さを調整し、素片レベル調整手段25でレベル調整した後、各素片を接続し、所望のピッチに対応した調和成分を生成して、非調和成分と合成する。
(特開2002-202790より)

◆音素ごとの繋がりについて

剣持 英語版の場合には、子音から子音につながる構造も、子音から無音につながる構造も、すべてサンプリングされて入っているということですね。

(the VOCALOID CV01 初音ミク 38頁より)

これは、特開2002-202790「歌唱合成装置」 の請求項4に記載された発明と思われます。

 

【請求項4】 前記音韻データベース中には、母音などの伸ばし音からなる音声素片データ、子音から母音あるいは母音から子音への音素連鎖からなる音声素片データ、子音か ら子音 への音素連鎖からなる音声素片データおよび母音から母音への音素連鎖からなる音声素片データが記憶されていることを特徴とする請求項1~3のいずれかに記 載の歌唱合成装置。 

(特開2002-202790 より)

◆子音のタイミング合わせについて

インタビュアー 「逆に言えば、Editor上で打ち込みをしているときは、Editor側で子音のタイミングを合わせてくれているのでしょうか。」

剣持 「そうです、子音を自動で前にシフトして合わせています。」

(the VOCALOID CV01 初音ミク 39頁より)

これは、子音の発生タイミングと音符の発生タイミングと同時にしたならば自然な歌唱にならないという課題を、子音の発生タイミングを少し前にシフトして合わせるという発明で解決したもので、特開2002-221978「ボーカルデータ生成装置、ボーカルデータ生成方法および歌唱音合成装置」が対応する特許出願とおもわれます。

【課題】 音節を構成する音素のうち、子音に対向する音素を音符の発生タイミングにあわせて発声することにより、伴奏に合わせたバーチャルシンガによる自然な歌唱を実現する。
【解決手段】 歌詞に対応した音節毎の発音タイミングデータを含むボーカルデータを予め記憶する。再生処理を始めると、音符「ド」に対応した音節「さ」を発声させるとき、子音「s」の発声動作を音符の発音タイミングよりも前に始め、母音「a」の発音タイミングを音符「ド」の発音タイミングに合わせる。これにより、伴奏に遅れることなく、バーチャルシンガによる自然な歌唱を可能にする。
(特開2002-2221978より)

◆合唱について

剣持 「あと、これはVOCALOIDシリーズに入るかどうかはわかりませんが、コーラスの合成技術も研究しています。」

(the VOCALOID CV01 初音ミク 39頁より)

合唱に関する特許出願は以下の2つと思われます。
特開2004-077608「合唱合成装置、合唱合成方法およびプログラム」
発明者は、劔持秀紀さんとジョルディ・ボナタさんです。

【課題】より自然な印象を聴取者に与えることが可能な合唱音を合成する。
【解決手段】この合唱合成装置100は、各々異なる音声に基づいて作成した3つの音声試料データ群110a,110b,110cを記憶する音声試料データベース110と、3つの歌唱生成器120,121,122とを有している。3パートからなる楽曲の合唱音信号を合成する際には、合唱制御部140の制御に下、歌唱生成器120,121,122は各々パートに歌詞情報やメロディ情報に応じて歌唱音信号を生成し、各合唱音信号を合成する。この生成の際に、各歌唱生成器120,121,122は異なる音声試料データ群110a,110b,110cに含まれる音声素片試料データを用いる。

(特開2004-077608より)

特開2006-251375「音声処理装置およびプログラム」
発明者は、劔持秀紀さん、吉岡靖雄さんとジョルディ・ボナタさんです。

【課題】 入力音声を簡易な構成によって多人数での合唱音や合奏音に変換する。
【解決手段】 ピッチ検出部12は、音声入力部61から供給される入力音声信号VinのピッチPinを検出する。エンベロープ検出部13は、入力音声信号Vinのスペクトルエンベロープを検出する。スペクトル取得手段30は、並列に発生された複数の音声を含む変換用音声の周波数スペクトルを取得する。ピッチ変換部21は、スペクトル取得手段30が取得した周波数スペクトルの各ピークの周波数をピッチPinに応じて変化させる。エンベロープ調整部22は、ピッチ変換部21による処理後の周波数スペクトルのスペクトルエンベロープをエンベロープ検出部13が検出したスペクトルエンベロープと略一致するように調整する。音声生成手段40は、エンベロープ調整部22による調整後の周波数スペクトルから出力音声信号Vnewを生成する。
(特開2006-251375より)

コーラスに関しては、論文でも発表されています。
Unisong: A Choir Singing Synthesizer
2006年10月に発表された論文で、著者は劔持秀紀さん、ジョルディボナダさん、Blaauw, Merlijnさん、Loscos, Alexさんの4名です。

Computer generated singing choir synthesis can be achieved by two means: clone transformation of a single voice or concatenation of real choir recording snippets. As of today, the synthesis quality for these two methods lack of naturalness and intelligibility respectively. Unisong is a new concatenation based choir singing synthesizer able to generate a high quality synthetic performance out of the score and lyrics specified by the user. This article describes all actions and techniques that take place in the process of virtual synthesis generation: choir recording scripts design and realization, human supervised automatic segmentation of the recordings, creation of samples database, and sample acquiring, transformation and concatenation. The synthesizer will be demonstrated with a song sample.

(Unisong A Choir Singing Synthesizer : Abstract より)

 コンピュータは合唱するように歌声を発生することを以下2つの方法で達成することができます: ただ一つの声のクローンによる変化か、又は本当のコーラス録音の連結です。現在において、これらの2つの方法の統合品質はそれぞれ自然さと明瞭さに欠けています。
 ユニソングは、スコアと歌詞によって高品質の合成音声の性能を得られるユーザ指定のコーラス歌声シンセサイザです。この記事は、仮想の統合世代の途中に行われるコーラス録音スクリプトの人間の監督された自動分割、サンプルデータベースの創造、サンプル取得、変化、および連結を実現する全ての動作とテクニックについて説明します。シンセサイザは歌のサンプルでデモンストレーションをするでしょう。
(参考訳)

'F-2 Voice Solo to Unison Choir Transformation'
2005年に発表された論文で、ジョルディ・ボナタさんが執筆しています。これはソロのボーカルをリアルタイムに多人数コーラスに変換する手法の論文のようです。

In this paper we present a transformation that pretends to convert a voice solo into a large, unison choir. The basic idea behind the presented algorithm is to morph the input voice solo (dry recording) with a recorded sustained vowel of a unison choir. The processing algorithm is based on the rigid phase-locked vocoder adapted to harmonic sounds. Pitch and timbre are taken from the voice solo, and the local spectrum comes out from the analysis of the unison choir sample.

(F-2 Voice Solo to Unison Choir Transformation)

 この論文では、私たちはソロの歌声を多人数コーラスに変換するふりをする変換について述べます。 提示されたアルゴリズムの後ろの基本的な考え方は入力声のソロの歌声(乾いた録音)を多人数コーラスの記録された持続している母音に変形することです。 処理アルゴリズムは倍音に適合させられたフェーズロック・ボコーダに基づいています。 ソロの歌声からピッチと音色を取ります、そして、多人数コーラスのサンプルの分析からローカルスペクトルを得ます。
(参考訳)

| | コメント (0) | トラックバック (1)

初音ミクに喋らせてみた(ピッチベンド利用)

やっとDTMマガジン1月号増刊「The Vocaloid CV01 初音ミク」が入手できました。

やはりヤマハ剣持氏のインタビューは面白かったですね。剣持氏といえば、12月30日のVocaloid Night Vol.2 でも登場されたそうです。年末は時間が取れなかったので自分はイベント等には行けなかったので、ちょっと残念に思っています。

この記事をもとに、自分が記載した「初音ミクの特許出願について 」の内容と照合してみます。

(1)VOCALOIDの開発開始時期の推定

自分は2002年にプロジェクトがスタートしたと推定したのですが、実際には2000年からプロジェクトがスタートしたそうです。推定と実際のズレの原因は、VOCALOIDの技術はフォルマント音声合成だと思い込んでおり、最後のチューニングが2002年の特許出願のピークだと判断したためです。実際にはフォルマント音声合成や連結型音声合成などの色々な方式を試す期間が必要であったのだろうと思われます。

(2)VOCALOIDの開発者数の推定

自分は10名から15名と推定したのですが、実際には主要メンバー2~3名+プログラマやテスターの方々が数名だったそうです。フォルマント音声合成の開発者を含めてカウントしてしまったのがズレの原因と思われます。

(3)主要開発者の推定

剣持さんが主要開発者であることは当たりました。

今回は、剣持氏のインタビュー内に記載された喋らせ方のコツ(38ページ)を読んで、VOCALOID Editor 上でミクの発音を修正してみました。流石は開発者のアドバイスですね、ミクの喋りがかなり自然になりました。

「tokkyo_2_pb.mp3」をダウンロード

「tokkyo_2_pb.vsq」をダウンロード

以前のバージョンでも、文節ごとの区切りと、音階によるアクセントの付与はおこなっていましたが、どうしても機械的になってしまいます。喋らせ方のコツに基づいて新たに行ったことは以下の2点です。

①ピッチベンド(PIT)を使用してアクセントを付与すること。音節ごとにピッチベンドのカーブを山なりにした。

②助詞と助動詞の発音を他と比して短くした。これにより品詞を理解して発音している様が表現できます。

その他、自分なりに新たに工夫したところは以下のものです。

③名詞の発音のVELを他と比して高くすること。これにより品詞を理解して発音している様が表現できます。

④OPEパラメータをPITと同様のカーブになるよう触ってみました。これはあまり利かないようです。

| | コメント (0) | トラックバック (1)

初音ミクに喋らせてみた(Perl版012)

miku_talk を、バージョンアップしてみました。年末ですから他のフリーソフト作者や職人の方々に遊んでいただこうという趣旨です。
今回の主なバージョンアップ機能は、任意のテキストを入力とできるようにしたことです。

「miku_talk012_1.zip」をダウンロード

以下、Readme.txt からの抜粋です。ちょっとだけインストールについて親切に記載してみました。

miku_talkとは:
 miku_talk は、自然文をもとに「VOCALOID2 初音ミク」の入出力ファイルを生成するソフトウエアです。

 miku_talk はフリーソフトウェアです.GPL(the GNU General Public License),  LGPL(Lesser GNU General Public License), または BSD ライセンスに従って 本ソフトウェアを使用,再配布することができます.  詳細は COPYING, GPL, LGPL, BSD各ファイルを参照して下さい.

動作環境:
 WindowsXP Home での動作を確認しています。UNIX/Linux 上で動作させる場合には、Mecab に入力する文字コードを EUC-JP に変更すれば動作するとおもいますが、未検証です。

インストール方法:
 事前に以下のインストールが必要となります。何れも無償で公開されています。なお、インストールは何れもWindowsXP が前提となっています。Unix/Linux では夫々のOSに適合したインストールをおこなってください。

  ActivePerl 5.8.x
   MeCab-096.exe
  Midi-Perl
   MeCab-Perl-binding

 ・・・・


この miku_talk012.pl を使って、前回のブログを初音ミクに読んでもらいました。ちょっとだけ手で修正したテキストを読ませています。

「test_miku012.mp3」をダウンロード

| | コメント (4) | トラックバック (0)

初音ミクに喋らせてみた(Perl版011)

Perl で漢字仮名混じり文から、VSQファイルを自動生成させてみました。形態素解析にはMecabを使用しています。Mecabは、自然文の読みまでを出力してくれるので、音声合成に楽に適用できます。
ここで、Mecab の設計者およびプログラマの方々に感謝いたします。

ミクに喋らせる文章は、特許法1条 「この法律は、発明の保護及び利用を図ることにより、発明を奨励し、もつて産業の発達に寄与することを目的とする。」 です。

「test_miku011.mp3」をダウンロード

「test_miku011.vsq」をダウンロード

今回は、アクセントっぽいのも入れてあります。あくまでテスト用の仮コーディングであり、標準語のアクセントではありません。

ソースコードはこちらです、UTF8の文字コードでセーブしてください。

#!/Perl
########################################################################
#    miku_talk ver.0.1.1
#
#   Programmed by Akira Izumi
#   Ver.0.0.1:ハードコーディング"みく" ...  6/Dec/2007
#   Ver.0.0.4:任意の平仮名入力を受付ける...15/Dec/2007
#   Ver.0.1.1:ソースをUTF8化し、形態素解析Mecabを組込...26/Dec/2007
#
use MIDI;
use Encode;
use MeCab;
use strict;
use warnings;

# my $myTalk = "発明とは、自然法則を利用した技術的思想の創作のうち高度のものをいう。";
  my $myTalk = "この法律は、発明の保護及び利用を図ることにより、発明を奨励し、もつて産業の発達に寄与することを目的とする。";
  miku_VsqGenerate($myTalk,"test_miku011.vsq");
  exit(0);

########################################################################
#
#   サブルーチン名:miku_VsqGenerate
#
#    日本語文字列からVSQファイルを生成する
#   第1引数:漢字仮名交じりのテキスト文字列
#   第2引数:出力VSQファイル名
#
#
sub miku_VsqGenerate {
my $myTalk  = $_[0];
my $myVsqFile = $_[1];

#
# マスタートラックのイベント定義。
#
my @masterEvents = (
  ['track_name',    0, 'Master Track'],
  ['set_tempo',     0, 500_000], # 1qn = .50 seconds
  ['time_signature',0,4,2,24,8 ],
  ['end_track' ,    0],
);
#
# 平仮名からミク発音記号への変換ハッシュ表
#
my %phonetic = (
"あ"=>"a",  "い"=>"i",   "う"=>"M",    "え"=>"e",    "お"=>"o",
"か"=>"k a","き"=>"k' i","く"=>"k M",  "け"=>"k e",  "こ"=>"k o",
"さ"=>"s a","し"=>"S i", "す"=>"s M",  "せ"=>"s e",  "そ"=>"s o",
"た"=>"t a","ち"=>"tS i","つ"=>"ts M", "て"=>"t e",  "と"=>"t o",
"な"=>"n a","に"=>"J i", "ぬ"=>"n M",  "ね"=>"n e",  "の"=>"n o",
"は"=>"h a","ひ"=>"C i", "ふ"=>"p\\ M","へ"=>"h e",  "ほ"=>"h o",
"ま"=>"m a","み"=>"m' i","む"=>"m M",  "め"=>"m e",  "も"=>"m o",
"や"=>"j a",             "ゆ"=>"j M",  "いぇ"=>"j e","よ"=>"j o",
"ら"=>"4 a","り"=>"4' i","る"=>"4 M",  "れ"=>"4 e",  "ろ"=>"4 o",
"わ"=>"w a","ゐ"=>"w i",
#        "ゑ"=>"w e",
"を"=>"o","うぃ"=>"w i",             "うぇ"=>"w e",
"ん"=>"n",
#"んが"=>"N a",   "んぎ"=>"N i",   "んぐ"=>"N M",   "んげ"=>"N e",   "んご"=>"N o",
#"んにゃ"=>"N' a","んにぃ"=>"N' i","んにゅ"=>"N' M","んにぇ"=>"N' e","んにょ"=>"N' o",

"が"=>"g a",   "ぎ"=>"g' i",  "ぐ"=>"g M",   "げ"=>"g e",   "ご"=>"g o",
"ざ"=>"dz a",  "じ"=>"dZ i",  "ず"=>"dz M",  "ぜ"=>"dz e",  "ぞ"=>"dz o",
"だ"=>"d a",   "ぢ"=>"dZ i",  "づ"=>"dz M",  "で"=>"d e",   "ど"=>"d o",
"ば"=>"b a",   "び"=>"b' i",  "ぶ"=>"b M",   "べ"=>"b e",   "ぼ"=>"b o",
"ぱ"=>"p a",   "ぴ"=>"p' i",  "ぷ"=>"p M",   "ぺ"=>"p e",   "ぽ"=>"p o",
"きゃ"=>"k' a","きぃ"=>"k' i","きゅ"=>"k' M","きぇ"=>"k' e","きょ"=>"k' o",
"しゃ"=>"S a", "しぃ"=>"S i", "しゅ"=>"S M", "しぇ"=>"S e", "しょ"=>"S o",
"ちゃ"=>"tS a","ちぃ"=>"tS i","ちゅ"=>"tS M","ちぇ"=>"tS e","ちょ"=>"tS o",
"にゃ"=>"J a", "にぃ"=>"J i", "にゅ"=>"J M", "にぇ"=>"J e", "にょ"=>"J o",
"ひゃ"=>"C a", "ひぃ"=>"C i", "ひゅ"=>"C M", "ひぇ"=>"C e", "ひょ"=>"C o",

"ふゃ"=>"p\\' a","ふぃ"=>"p\\' i","ふゅ"=>"p\\' M","ふぇ"=>"p\\' e","ふょ"=>"p\\' o",
"みゃ"=>"m' a","みぃ"=>"m' i","みゅ"=>"m' M","みぇ"=>"m' e","みょ"=>"m' o",
"りゃ"=>"4' a","りぃ"=>"4' i","りゅ"=>"4' M","りぇ"=>"4' e","りょ"=>"4' o",
"ぎゃ"=>"g' a","ぎぃ"=>"g' i","ぎゅ"=>"g' M","ぎぇ"=>"g' e","ぎょ"=>"g' o",
"じゃ"=>"Z a", "じぃ"=>"Z i", "じゅ"=>"Z M", "じぇ"=>"Z e", "じょ"=>"Z o",
"じゃ"=>"dZ a","じぃ"=>"dZ i","じゅ"=>"dZ M","じぇ"=>"dZ e","じょ"=>"dZ o",
"ぢゃ"=>"dZ a","ぢぃ"=>"dZ i","ぢゅ"=>"dZ M","ぢぇ"=>"dZ e","ぢょ"=>"dZ o",
"びゃ"=>"b' a","びぃ"=>"b' i","びゅ"=>"b' M","びぇ"=>"b' e","びょ"=>"b' o",
"ぴゃ"=>"p' a","ぴぃ"=>"p' i","ぴゅ"=>"p' M","ぴぇ"=>"p' e","ぴょ"=>"p' o",
"ふぁ"=>"p\\ a","ふぃ"=>"p\\ i","ふぅ"=>"p\\ M","ふぇ"=>"p\\ e","ふぉ"=>"p\\ o",
"てゃ"=>"t' a","てぃ"=>"t' i","てゅ"=>"t' M","てぇ"=>"t' e","てょ"=>"t' o",
"でゃ"=>"d' a","でぃ"=>"d' i","でゅ"=>"d' M","でぇ"=>"d' e","でょ"=>"d' o",
"ぁ"=>"h\\ a", "ぃ"=>"h\\ i",  "ぅ"=>"h\\ M","ぇ"=>"h\\ e", "ぉ"=>"h\\ o",
"っ"=>"tS  ",
"すぃ"=>"s i", "ずぃ"=>"dz i", "とぅ"=>"t M","どぅ"=>"d M",
"ア"=>"a",  "イ"=>"i",   "ウ"=>"M",    "エ"=>"e",    "オ"=>"o",
"カ"=>"k a","キ"=>"k' i","ク"=>"k M",  "ケ"=>"k e",  "コ"=>"k o",
"サ"=>"s a","シ"=>"S i", "ス"=>"s M",  "セ"=>"s e",  "ソ"=>"s o",
"タ"=>"t a","チ"=>"tS i","ツ"=>"ts M", "テ"=>"t e",  "ト"=>"t o",
"ナ"=>"n a","ニ"=>"J i", "ヌ"=>"n M",  "ネ"=>"n e",  "ノ"=>"n o",
"ハ"=>"h a","ヒ"=>"C i", "フ"=>"p\\ M","ヘ"=>"h e",  "ホ"=>"h o",
"マ"=>"m a","ミ"=>"m' i","ム"=>"m M",  "メ"=>"m e",  "モ"=>"m o",
"ヤ"=>"j a",             "ユ"=>"j M",  "イェ"=>"j e","ヨ"=>"j o",
"ラ"=>"4 a","リ"=>"4' i","ル"=>"4 M",  "レ"=>"4 e",  "ロ"=>"4 o",
"ワ"=>"w a","ヰ"=>"w i",
#        "ヱ"=>"w e",
"ヲ"=>"o",
             "ウィ"=>"w i",             "ウェ"=>"w e",
"ン"    =>"n",
#"ンガ"  =>"N a", "ンギ"=>"N i",   "ング"=>"N M",   "ンゲ"=>"N e",   "ンゴ"=>"N o",
#"ンニャ"=>"N' a","ンニィ"=>"N' i","ンニュ"=>"N' M","ンニェ"=>"N' e","ンニョ"=>"N' o",
"ガ"=>"g a",   "ギ"=>"g' i",  "グ"=>"g M",   "ゲ"=>"g e",   "ゴ"=>"g o",
"ザ"=>"dz a",  "ジ"=>"dZ i",  "ズ"=>"dz M",  "ゼ"=>"dz e",  "ゾ"=>"dz o",
"ダ"=>"d a",   "ヂ"=>"dZ i",  "ヅ"=>"dz M",  "デ"=>"d e",   "ド"=>"d o",
"バ"=>"b a",   "ビ"=>"b' i",  "ブ"=>"b M",   "ベ"=>"b e",   "ボ"=>"b o",
"パ"=>"p a",   "ピ"=>"p' i",  "プ"=>"p M",   "ペ"=>"p e",   "ポ"=>"p o",
#                             "ヴ"=>""p M",
"キャ"=>"k' a","キィ"=>"k' i","キュ"=>"k' M","キェ"=>"k' e","キョ"=>"k' o",
"シャ"=>"S a", "シィ"=>"S i", "シュ"=>"S M", "シェ"=>"S e", "ショ"=>"S o",
"チャ"=>"tS a","チィ"=>"tS i","チュ"=>"tS M","チェ"=>"tS e","チョ"=>"tS o",
"ニャ"=>"J a", "ニィ"=>"J i", "ニュ"=>"J M", "ニェ"=>"J e", "ニョ"=>"J o",
"ヒャ"=>"C a", "ヒィ"=>"C i", "ヒュ"=>"C M", "ヒェ"=>"C e", "ヒョ"=>"C o",

"フャ"=>"p\\' a","フィ"=>"p\\' i","フュ"=>"p\\' M","フェ"=>"p\\' e","フョ"=>"p\\' o",
"ミャ"=>"m' a",  "ミィ"=>"m' i",  "ミュ"=>"m' M",  "ミェ"=>"m' e",  "ミョ"=>"m' o",
"リャ"=>"4' a",  "リィ"=>"4' i",  "リュ"=>"4' M",  "リェ"=>"4' e",  "リョ"=>"4' o",
"ギャ"=>"g' a","ギィ"=>"g' i","ギュ"=>"g' M","ギェ"=>"g' e","ギョ"=>"g' o",
"ジャ"=>"Z a", "ジィ"=>"Z i", "ジュ"=>"Z M", "ジェ"=>"Z e", "ジョ"=>"Z o",
"ジャ"=>"dZ a","ジィ"=>"dZ i","ジュ"=>"dZ M","ジェ"=>"dZ e","ジョ"=>"dZ o",
"ヂャ"=>"dZ a","ヂィ"=>"dZ i","ヂュ"=>"dZ M","ビェ"=>"dZ e","ビョ"=>"dZ o",
"ビャ"=>"b' a","ビィ"=>"b' i","ビュ"=>"b' M","ビェ"=>"b' e","ビョ"=>"b' o",
"ピャ"=>"p' a","ピィ"=>"p' i","ピュ"=>"p' M","ピェ"=>"p' e","ピョ"=>"p' o",
"ファ"=>"p\\ a","フィ"=>"p\\ i","フゥ"=>"p\\ M","フェ"=>"p\\ e","フォ"=>"p\\ o",
"テャ"=>"t' a", "ティ"=>"t' i", "テゥ"=>"t' M", "テェ"=>"t' e", "テォ"=>"t' o",
"デャ"=>"d' a", "ディ"=>"d' i", "デゥ"=>"d' M","デェ"=>"d' e",  "デォ"=>"d' o",
"ァ"=>"h\\ a", "ィ"=>"h\\ i",   "ゥ"=>"h\\ M", "ェ"=>"h\\ e",   "ォ"=>"h\\ o",
"ッ"=>"tS  ",
"スィ"=>"s i", "ズィ"=>"dz i", "トゥ"=>"t M","ドゥ"=>"d M");
#
my %phonetic_class = (
"ー"=>"長音",
"-"=>"長音",
"-"=>"長音"
);

#
# ミクの発音用テキストに於ける初期値の設定。
#
  my @myCommonSection =();
  push @myCommonSection, "[Common]";
  push @myCommonSection, "Version=DSB301";
  push @myCommonSection, "Name=Voice1";
  push @myCommonSection, "Color=181,162,123";
  push @myCommonSection, "DynamicsMode=1";
  push @myCommonSection, "PlayMode=1";

  my @myMasterSection =();
  push @myMasterSection, "[Master]";
  push @myMasterSection, "PreMeasure=4";

  my @myMixerSection =();
  push @myMixerSection, "[Mixer]";
  push @myMixerSection, "MasterFeder=0";
  push @myMixerSection, "MasterPanpot=0";
  push @myMixerSection, "MasterMute=0";
  push @myMixerSection, "OutputMode=0";
  push @myMixerSection, "Tracks=1";
  push @myMixerSection, "Feder0=0";
  push @myMixerSection, "Panpot0=0";
  push @myMixerSection, "Mute0=0";
  push @myMixerSection, "Solo0=0";

  my @myEventListSection =();
  push @myEventListSection, "[EventList]";
  push @myEventListSection, "0=ID#0000";

  my @myIDSection =();
  push @myIDSection, "[ID#0000]";
  push @myIDSection, "Type=Singer";
  push @myIDSection, "IconHandle=h#0000";

  my @myHandleSection =();
  push @myHandleSection, "[h#0000]";
  push @myHandleSection, "IconID=\$07010000";
  push @myHandleSection, "IDS=Miku";
  push @myHandleSection, "Original=0";
  push @myHandleSection, "Caption=";
  push @myHandleSection, "Length=1";
  push @myHandleSection, "Language=0";
  push @myHandleSection, "Program=0";

  my @mikuMidiEvents = ();
  push @mikuMidiEvents,['control_change' , 0, 0,  99, 96];
  push @mikuMidiEvents,['control_change' , 0, 0,  98,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,   6,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,  38,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,  98,  1];
  push @mikuMidiEvents,['control_change' , 0, 0,   6,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,  38,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,  98,  2];
  push @mikuMidiEvents,['control_change' , 0, 0,   6,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,  99, 83];
  push @mikuMidiEvents,['control_change' , 0, 0,  98,  2];
  push @mikuMidiEvents,['control_change' , 0, 0,   6,  0];

#
# ミク発音(平仮名)を、ミク発音用メタデータに変換し、
#  同時にMIDIイベントを生成する。
#
  my $i=0;
  my $pitch = 180;
  my $note = 64;
  my $myIdPos = 7680;
  my $myIdPosLast = $myIdPos;
  my $myHinsiLast = "";

  Encode::from_to($myTalk,"UTF8","shiftjis");

  my $mecab = MeCab::Tagger->new();
  my $node = $mecab->parseToNode($myTalk);
  for( ; $node; $node = $node->{next} ) {
    next unless defined $node->{surface};
    my $midasi = $node->{surface};
    my( $hinsi, $yomi ) = (split( /,/, $node->{feature} ))[0,8];
    if( $hinsi eq "BOS/EOS" ) {
      next;
    }
print $midasi, "\t<", $yomi, ">\t", $hinsi, "\n";

#
# 文節の区切りを判断して、発音間隔を空ける
# アクセント($note) は仮
#
    Encode::from_to($hinsi,"shiftjis","UTF8");
    if( ( $hinsi eq "名詞" || $hinsi eq "動詞" || $hinsi eq "形容詞" || $hinsi eq "形容動詞" )
    && ($myHinsiLast eq "助詞" || $myHinsiLast eq "接続詞" || $myHinsiLast eq "記号") ) {
      $myIdPos += $pitch;
      $note = 64;
    }
    if( $hinsi eq "記号" ) {
      $note = 64;
    }
    my $idxLyric = 0;
    my $j=0;
    for($j=0; $idxLyric<length($yomi); $j++,$i++) {
      my $myLyricLen = 6;
      my $myLyric = "";
      my $myLyric_utf8 = "";
      my $myPhonetic = "";
      for($myLyricLen=6; $myLyricLen>0; $myLyricLen-=2) {
        $myLyric_utf8 = $myLyric = substr($yomi,$idxLyric,$myLyricLen);
        Encode::from_to($myLyric_utf8,"shiftjis","UTF8");
        $myPhonetic = $phonetic{$myLyric_utf8};
        if( defined($myPhonetic) || $myLyricLen==2 ) {
          last;
        }
      }
      $idxLyric += $myLyricLen;
      my $myLength = $pitch;
      if( $idxLyric + 2 <= length($yomi) ){
        $myLyric_utf8 = substr($yomi,$idxLyric,2);
        Encode::from_to($myLyric_utf8,"shiftjis","UTF8");
        if( $myLyric_utf8 eq "ー" ) {
          $myLength += $pitch;
          $idxLyric += 2;
        }
      }
      if( defined($myPhonetic)) {
        push @myEventListSection, sprintf("%d=ID#%04d",$myIdPos,$i+1);
        push @myIDSection, sprintf("[ID#%04d]",$i+1);
        push @myIDSection, "Type=Anote";
        push @myIDSection, "Length=".$myLength;
        push @myIDSection, "Note#=".$note;
        push @myIDSection, "Dynamics=64";
        push @myIDSection, "PMBendDepth=20";
        push @myIDSection, "PMBendLength=0";
        push @myIDSection, "PMbPortamentoUse=0";
        push @myIDSection, "DEMdecGainRate=50";
        push @myIDSection, "DEMaccent=50";
        push @myIDSection, sprintf("LyricHandle=h#%04d",$i+1);
   
        push @myHandleSection, sprintf("[h#%04d]",$i+1);
       
        push @myHandleSection, "L0=\"".$myLyric."\",\"". $myPhonetic."\",1.000000,64,0,0";
        $myIdPos += $myLength;
#  print "L0=\"".$myLyric."\",\"". $myPhonetic."\",1.000000,64,0,0","\n";
        if( $i==0 ) {
          push @mikuMidiEvents,['control_change', 5760, 0, 99,  80];
        } else {
          push @mikuMidiEvents,['control_change', $myIdPos - $myIdPosLast, 0, 99,  80];
        }
        push @mikuMidiEvents,['control_change', 0, 0, 98,   0];
        push @mikuMidiEvents,['control_change', 0, 0,  6,   0];
        push @mikuMidiEvents,['control_change', 0, 0, 38,   0];
        push @mikuMidiEvents,['control_change', 0, 0, 98,   1];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  15];
        push @mikuMidiEvents,['control_change', 0, 0, 38,  80];
        push @mikuMidiEvents,['control_change', 0, 0, 98,   2];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  64];
        push @mikuMidiEvents,['control_change', 0, 0, 98,   3];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  64];
        push @mikuMidiEvents,['control_change', 0, 0, 98,   4];
        push @mikuMidiEvents,['control_change', 0, 0,  6,   1];
        push @mikuMidiEvents,['control_change', 0, 0, 38, 122];
        push @mikuMidiEvents,['control_change', 0, 0, 98,   5];
        push @mikuMidiEvents,['control_change', 0, 0,  6,   1];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  18];
        push @mikuMidiEvents,['control_change', 0, 0,  6,   3];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  19];
        push @mikuMidiEvents,['control_change', 0, 0,  6, 109];
        push @mikuMidiEvents,['control_change', 0, 0, 38,  64];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  20];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  39];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  21];
        push @mikuMidiEvents,['control_change', 0, 0,  6, 105];
        push @mikuMidiEvents,['control_change', 0, 0, 38,   0];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  79];
        push @mikuMidiEvents,['control_change', 0, 0,  6, 127];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  80];
        push @mikuMidiEvents,['control_change', 0, 0, 6,   12];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  81];
        push @mikuMidiEvents,['control_change', 0, 0,  6,   8];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  82];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  20];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  83];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  28];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  84];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  24];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  85];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  10];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  86];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  12];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  87];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  12];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  88];
        push @mikuMidiEvents,['control_change', 0, 0,  6,   0];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  89];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  50];
        push @mikuMidiEvents,['control_change', 0, 0, 98,  90];
        push @mikuMidiEvents,['control_change', 0, 0,  6,  50];
        push @mikuMidiEvents,['control_change', 0, 0, 98, 127];
        push @mikuMidiEvents,['control_change', 0, 0,  6, 127];
        $myIdPosLast = $myIdPos;
      } else {
        $myIdPos += $myLength;
#  print "No Phonetic\n";
      }
      if($note == 64) {
        $note = 65;
      }
    }
    $myHinsiLast = $hinsi;
  }
  push @mikuMidiEvents,['end_track' , $pitch+1920];
  push @myEventListSection, sprintf("%d=EOS",$i*$pitch+7620);
#
#  ミク発音用メタデータのセクションを結合する
#
  my $my_miku_phonetics="";
  my $phonetic = "";
  foreach $phonetic (@myCommonSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myMasterSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myMixerSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myEventListSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myIDSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myHandleSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
#
#  Voice1トラックのイベントを生成する。
#
my @voice1Events = (
  ['track_name',    0, 'Voice1'],
);
  for($i=0; $i*119<length($my_miku_phonetics); $i++) {
    push @voice1Events, ['text_event', 0,
      sprintf("DM:%04d:",$i).substr($my_miku_phonetics,$i*119,119) ];
  }
  my $mikuMidi = "";
  foreach $mikuMidi (@mikuMidiEvents) {
    push @voice1Events,$mikuMidi;
  }
#
# マスタートラックとVoice1トラックからVSQファイルを生成する。
#
  my $master_track = MIDI::Track->new({ 'events' => \@masterEvents });
  my $voice1_track = MIDI::Track->new({ 'events' => \@voice1Events });
  my $opus = MIDI::Opus->new(
    { 'format' => 1, 'ticks' => 480, 'tracks' => [ $master_track, $voice1_track ] } );
  $opus->write_to_file( $myVsqFile );
}

| | コメント (0) | トラックバック (1)

「著作権の効力の制限」を考えてみる #3

こちらの記事を拝見しましたので、この記事をもとに自分なりに著作権法38条についてコメントしてみます。

なんで著作権法38条が話題にのぼらないんだ?
http://anond.hatelabo.jp/20071218190036

ここで、著作権法38条をご紹介します。(法令データ提供システムより)

第三十八条  公表された著作物は、営利を目的とせず、かつ、聴衆又は観衆から料金(いずれの名義をもつてするかを問わず、著作物の提供又は提示につき受ける対価をい う。以下この条において同じ。)を受けない場合には、公に上演し、演奏し、上映し、又は口述することができる。ただし、当該上演、演奏、上映又は口述につ いて実演家又は口述を行う者に対し報酬が支払われる場合は、この限りでない。
 放送される著作物は、営利を目的とせず、かつ、聴衆又は観衆から料金を受けない場合には、有線放送し、又は専ら当該放送に係る放送対象地域にお いて受信されることを目的として自動公衆送信(送信可能化のうち、公衆の用に供されている電気通信回線に接続している自動公衆送信装置に情報を入力するこ とによるものを含む。)を行うことができる。
 放送され、又は有線放送される著作物(放送される著作物が自動公衆送信される場合の当該著作物を含む。)は、営利を目的とせず、かつ、聴衆又は 観衆から料金を受けない場合には、受信装置を用いて公に伝達することができる。通常の家庭用受信装置を用いてする場合も、同様とする。
 公表された著作物(映画の著作物を除く。)は、営利を目的とせず、かつ、その複製物の貸与を受ける者から料金を受けない場合には、その複製物 (映画の著作物において複製されている著作物にあつては、当該映画の著作物の複製物を除く。)の貸与により公衆に提供することができる。
 映画フィルムその他の視聴覚資料を公衆の利用に供することを目的とする視聴覚教育施設その他の施設(営利を目的として設置されているものを除 く。)で政令で定めるものは、公表された映画の著作物を、その複製物の貸与を受ける者から料金を受けない場合には、その複製物の貸与により頒布することが できる。この場合において、当該頒布を行う者は、当該映画の著作物又は当該映画の著作物において複製されている著作物につき第二十六条に規定する権利を有 する者(第二十八条の規定により第二十六条に規定する権利と同一の権利を有する者を含む。)に相当な額の補償金を支払わなければならない。

 非営利目的の実演などの場合には、かなり幅広い著作権の効力の制限が認められていることが判ります。音楽を学ぶという場合には、他人の楽曲をそのまま実演することが多いからです。著作権の効力に制限を加えて、他人の楽曲を練習する機会を与えることは、文化の発展(著作権法1条)に寄与すると思われます。これは丁度、試験または研究には特許権が及ばない(特許法69条)と同様の趣旨です。
 然るに、その他人の著作物(楽曲など)を実演したものを非営利目的でネットワークにアップロードしたらどうなるか。これは自動公衆送信(23条)に該当し、著作権法38条1項の「上演し、演奏し、上映し、又は口述」に該当しないため、少なくとも38条1項の例外規定には含まれません。よって非営利目的であっても著作権が及び、権利者が申し立てたならば差止等を受けることになります。
 しかし、著作権法38条2項には、放送される著作物は非営利目的ならば自動公衆送信により放送できることが記載されていることを鑑みると、他人の著作物の実演かつ非営利目的ならば自動公衆送信することを許して良いようにも思われます。ニコニコ動画などで、視聴者が寄せるコメントが、その実演を更に良いものへとブラッシュアップする役割を果たし、更に良いものを生み出しているからです。これは文化の発展の法目的に寄与すると判断します。
 よって、非営利目的ならば、他人の著作物の実演を公衆送信することに著作権が及ばないよう著作権法が改正されることを期待いたします。

| | コメント (0) | トラックバック (0)

「著作権の効力の制限」を考えてみる #2

法政大学の白田先生が、こちらに面白い記事を書いておられますので紹介します。

もう一つの著作権の話
http://orion.mt.tama.hosei.ac.jp/hideaki/another.htm

 著作権なき時代にも人は創作活動をしていた訳だから、人は必ずしも著作権による著作物の専有を目的として著作物を創作する訳ではないという趣旨の指摘には、思わずはっとしました。それは、自分が何ら金にもならないのに、初音ミクに喋らせるツール miku_talk.pl を作ろうとしている事も同様とおもいます。
 たぶん、自分はリン・レンは買って互換性チェックしたり、リン・レンの読上げツールを作成するとおもいますし、金と時間が許せばMEIKO/KAITO も扱いたいとおもいます。

白田先生のHPはこちらですね。

Research Papers of Hideaki Shirata
http://orion.mt.tama.hosei.ac.jp/hideaki/indexj.htm

こういう頁もあったりします。

Thanksgiving Day
http://orion.mt.tama.hosei.ac.jp/hideaki/thanksgiving.htm

| | コメント (0) | トラックバック (0)

「著作権の効力の制限」を考えてみる

著作権法は著作者保護を目的とする法律ではありません。目的は「文化の発展」であり(著作権法1条)、その目的を達するために第5款で、著作権の効力の制限が記載されています。

30条:私的使用のための複製
31条:図書館等における複製
32条:引用
33条:教科書図書等への複製
33条の2:教科用拡大図書等の作成のための複製
34条:学校教育番組の放送等
35条:学校その他の教育機関における複製等
36条:試験問題としての複製等
37条:点字による複製等
37条の2:聴覚障害者のための自動公衆送信
38条:営利を目的としない上演等
39条:時事問題に関する論説の転載等
40条:政治上の演説等の利用
41条:時事の事件の報道のための利用
42条:裁判手続等における複製
42条の2:行政機関情報公開法等による開示のための利用
43条:翻訳、翻案による利用
44条:放送事業者等による一時的固定
45条:美術の著作物等の原作品の所有者による展示
46条:公開の美術の著作物等の利用
47条:美術の著作物等の展示に伴う複製
47条の2:プログラムの著作物の複製物の所有者による複製等
47条の3:複製権の制限により作成された複製物の譲渡

公開の美術の著作物等については、利用又は二次利用することができます。(46条)公開された美術作品の利用が著作権により制約されるとするならば、新た著作活動を阻害し、文化の発展に寄与しなくなる恐れがあるためです。

 

(公開の美術の著作物等の利用)

第四十六条  美術の著作物でその原作品が前条第二項に規定する屋外の場所に恒常的に設置されているもの又は建築の著作物は、次に掲げる場合を除き、いずれの方法によるかを問わず、利用することができる。
 彫刻を増製し、又はその増製物の譲渡により公衆に提供する場合
 建築の著作物を建築により複製し、又はその複製物の譲渡により公衆に提供する場合
 前条第二項に規定する屋外の場所に恒常的に設置するために複製する場合
 専ら美術の著作物の複製物の販売を目的として複製し、又はその複製物を販売する場合

ここでいう「前条第二項に規定する屋外の場所」とは、街路、公園その他一般公衆に開放されている屋外の場所又は建造物の外壁その他一般公衆の見やすい屋外の場所をいいます。(著作権法45条2項)

著作権法46条に規定されているのは、美術の著作物で、原作品が45条2項に規定する屋外の場所に恒常的に設置されているものと、建築の著作物に限定されています。
しかし、46条の趣旨から、音楽の著作物で恒常的にインターネットで一般公衆に公開されているものは、自由に利用可能とする事が文化の発展に寄与すると判断します。

ニコニコ動画へのアップロードが、「一般公衆に公開」に該当するかは議論の余地があります。ニコニコ動画は登録ユーザーのみに公開されたシステムだからです。自分は、メールアカウントの登録のみで一般会員になれるという緩い制限しかないため、ニコニコ動画は「一般公衆に公開」にあたると解釈いたします。

将来的にはインターネットで一般公衆に公開された音楽の著作物は、少なくとも一般公衆に公開されつづけている限りにおいて、自由に利用可能とするように法改正がなされる事を希望いたします。

| | コメント (0) | トラックバック (0)

初音ミク関連ソフトウエア・リンク集

Vocalips を作られたzhuoさんが、初音ミク関連ソフトウエア・リンク集を作成いただきました、当該ブログにもリンクを貼っていただき、ありがとうございます。>zhuoさん。

Software Study Notes
http://www.geocities.jp/zhuoware/software_study.html

VOCALOID2 には、まだまだ色々な周辺ソフトウエアが出てくる余地があると思います。初音ミク VOCALOID2 はいわば、「音声合成ソフトウエアのアセンブラ」であり、時間を労力を膨大に費やして、やっと人前に出せる作品ができるという代物ですが、もっと直感的に簡単に楽しくVOCALOIDで音楽が作れるようになれば、世の中を変えるムーブメントすら起こせるかもしれない。そんな可能性を垣間見せてくれる商品です。

また、十数年もの長きにわたりYAMAHAが挑戦してきた音声合成技術が、研究と商品化の間に横たわる「死の谷」を超えて、商品として羽ばたきつつあるのが興味深いです。

| | コメント (0) | トラックバック (0)

「みくみくにしてあげる♪」がJASRAC信託に

 初音ミク・オリジナル曲「みくみくにしてあげる♪」は、先週JASRAC信託となりました。ということは、当該ブログで紹介しているyoutubeのリンクはブログ内のウインドウで再生されることにより、当該ブログがストリーム配信を行っていると解される恐れがあります。これは公衆送信権(著作権23条)の侵害を構成していると解される恐れを有することと同一です。対策として、「みくみくにしてあげる♪」を含め、youtube にリンクしている初音ミク・オリジナル曲のハイパーリンクは全て削除しました。今後、他のオリジナル曲がJASRAC管理下になった場合に備えてです。
 ニコニコ動画のリンクは消していません。ニコニコ動画の場合には別ウインドウが開くため当該ブログは引用(著作権32条)しているに過ぎず、ストリーム配信に該当しないと解される事と、ドワンゴは「みくみくにしてあげる♪」の公衆送信権を有しているのではないかと思われるからです。
 詳しくは、この週末にJASRAC規約を読んで判断したいと思います。

 無事に弁理士登録を終わりましたので、会社で「弁理士」と呼ばれるのですが、まだなんとなくしっくりとこないです。某所で呼ばれた「アキバ系弁理士」という呼称が妙に気に入ったので、ブログのサブタイトルを併せて変更します。

| | コメント (0) | トラックバック (0)

melody...3D PV ver1.50

初音ミクの3Dモデリングを用いたオリジナル曲のプロモーションビデオ(PV)は幾つかありますが、あまりにも演出の出来が良すぎるので備忘録としてリンクを貼ります。

コメントの数が再生数より多いのも特筆ものです、いま現在で再生3239、コメント3366です。

| | コメント (0) | トラックバック (0)

初音ミクに喋らせてみた(Perl版004)

初音ミクに喋らせるスクリプトをちょっとだけバージョンアップしてみました。
相変わらずハードコーディングですが、$myTalk の文字列(平仮名のみ限定)を書き換えることで、任意文字列の発音ができるようにしています。

ハードコーディングしている理由は、エラー処理をしていない為です。たぶん半角文字やカタカナを入れるとミクが黙りこむとおもいます。親切に実行手順を書いていないのは、「まだα版なので、わかる人だけ触ってください」という趣旨です。

Perl スクリプトと、生成される VSQファイルは以下のものです。
「miku_talk004.zip」をダウンロード

生成される音声は「わたしわ、はつねみく。わたしわ、しゃべるのがすき」です。音声ファイルと照合してください。
「test_miku004.mp3」をダウンロード

そして、ソースコードはこちら。ちょっとだけ手を入れて美化。

#!/Perl
########################################################################
#    miku_talk ver.0.0.4
#
#   Programmed by Akira Izumi
#   Ver.0.0.1:ハードコーディング"みく" ...  6/Dec/2007
#   Ver.0.0.4:任意の平仮名入力を受付ける...15/Dec/2007
#
use MIDI;
use Jcode;
use strict;
use warnings;

  my $myTalk = "わたしわ、はつねみく、わたしわ、しゃべるのがすき。";
  miku_VsqGenerate($myTalk,"test_miku004.vsq");
  exit(0);
#-----------------------------------------------------------------------
#
#    平仮名文字列からVSQファイルを生成する
#   第1引数:平仮名のみのテキスト文字列
#   第2引数:出力VSQファイル名
#
sub miku_VsqGenerate {
my $myStr2Talk  = $_[0];
my $myVsqFile   = $_[1];

#
# マスタートラックの定義
#
my @masterEvents = (
  ['track_name',    0, 'Master Track'],
  ['set_tempo',     0, 500_000], # 1qn = .50 seconds
  ['time_signature',0,4,2,24,8 ],
  ['end_track' ,    0],
);
#
# 平仮名からミク発音記号への変換ハッシュ表
#
my %phonetic =
("あ"=>"a",  "い"=>"i",   "う"=>"M",    "え"=>"e",    "お"=>"o",
"か"=>"k a","き"=>"k' i","く"=>"k M",  "け"=>"k e",  "こ"=>"k o",
"さ"=>"s a","し"=>"S i", "す"=>"s M",  "せ"=>"s e",  "そ"=>"s o",
"た"=>"t a","ち"=>"tS i","つ"=>"ts M", "て"=>"t e",  "と"=>"t o",
"な"=>"n a","に"=>"J i", "ぬ"=>"n M",  "ね"=>"n e",  "の"=>"n o",
"は"=>"h a","ひ"=>"C i", "ふ"=>"p\\ M","へ"=>"h e",  "ほ"=>"h o",
"ま"=>"m a","み"=>"m' i","む"=>"m M",  "め"=>"m e",  "も"=>"m o",
"や"=>"j a",             "ゆ"=>"j M",  "いぇ"=>"j e","よ"=>"j o",
"ら"=>"4 a","り"=>"4' i","る"=>"4 M",  "れ"=>"4 e",  "ろ"=>"4 o",
"わ"=>"w a",
#            "ゐ"=>"w i",        "ゑ"=>"w e",
  "を"=>"o",
             "うぃ"=>"w i",             "うぇ"=>"w e",
"ん"=>"n",
"んが"=>"N a",   "んぎ"=>"N i",   "んぐ"=>"N M",   "んげ"=>"N e",   "んご"=>"N o",
"んにゃ"=>"N' a","んにぃ"=>"N' i","んにゅ"=>"N' M","んにぇ"=>"N' e","んにょ"=>"N' o",

"が"=>"g a",   "ぎ"=>"g' i",  "ぐ"=>"g M",   "げ"=>"g e",   "ご"=>"g o",
"ざ"=>"dz a",  "じ"=>"dZ i",  "ず"=>"dz M",  "ぜ"=>"dz e",  "ぞ"=>"dz o",
"だ"=>"d a",   "ぢ"=>"dZ i",  "づ"=>"dz M",  "で"=>"d e",   "ど"=>"d o",
"ば"=>"b a",   "び"=>"b' i",  "ぶ"=>"b M",   "べ"=>"b e",   "ぼ"=>"b o",
"ぱ"=>"p a",   "ぴ"=>"p' i",  "ぷ"=>"p M",   "ぺ"=>"p e",   "ぽ"=>"p o",
"きゃ"=>"k' a","きぃ"=>"k' i","きゅ"=>"k' M","きぇ"=>"k' e","きょ"=>"k' o",
"しゃ"=>"S a", "しぃ"=>"S i", "しゅ"=>"S M", "しぇ"=>"S e", "しょ"=>"S o",
"ちゃ"=>"tS a","ちぃ"=>"tS i","ちゅ"=>"tS M","ちぇ"=>"tS e","ちょ"=>"tS o",
"にゃ"=>"J a", "にぃ"=>"J i", "にゅ"=>"J M", "にぇ"=>"J e", "にょ"=>"J o",
"ひゃ"=>"C a", "ひぃ"=>"C i", "ひゅ"=>"C M", "ひぇ"=>"C e", "ひょ"=>"C o",

"ふゃ"=>"p\\' a","ふぃ"=>"p\\' i","ふゅ"=>"p\\' M","ふぇ"=>"p\\' e","ふょ"=>"p\\' o",
"みゃ"=>"m' a","みぃ"=>"m' i","みゅ"=>"m' M","みぇ"=>"m' e","みょ"=>"m' o",
"りゃ"=>"4' a","りぃ"=>"4' i","りゅ"=>"4' M","りぇ"=>"4' e","りょ"=>"4' o",
"ぎゃ"=>"g' a","ぎぃ"=>"g' i","ぎゅ"=>"g' M","ぎぇ"=>"g' e","ぎょ"=>"g' o",
"じゃ"=>"Z a", "じぃ"=>"Z i", "じゅ"=>"Z M", "じぇ"=>"Z e", "じょ"=>"Z o",
"じゃ"=>"dZ a","じぃ"=>"dZ i","じゅ"=>"dZ M","じぇ"=>"dZ e","じょ"=>"dZ o",
"ぢゃ"=>"dZ a","ぢぃ"=>"dZ i","ぢゅ"=>"dZ M","ぢぇ"=>"dZ e","ぢょ"=>"dZ o",
"びゃ"=>"b' a","びぃ"=>"b' i","びゅ"=>"b' M","びぇ"=>"b' e","びょ"=>"b' o",
"ぴゃ"=>"p' a","ぴぃ"=>"p' i","ぴゅ"=>"p' M","ぴぇ"=>"p' e","ぴょ"=>"p' o",
"ふぁ"=>"p\\ a","ふぃ"=>"p\\ i","ふぅ"=>"p\\ M","ふぇ"=>"p\\ e","ふぉ"=>"p\\ o",
"てゃ"=>"t' a","てぃ"=>"t' i","てゅ"=>"t' M","てぇ"=>"t' e","てょ"=>"t' o",
"でゃ"=>"d' a","でぃ"=>"d' i","でゅ"=>"d' M","でぇ"=>"d' e","でょ"=>"d' o",
"ぁ"=>"h\\ a", "ぃ"=>"h\\ i",  "ぅ"=>"h\\ M","ぇ"=>"h\\ e", "ぉ"=>"h\\ o",
"っ"=>"tS  ",
"すぃ"=>"s i", "ずぃ"=>"dz i", "とぅ"=>"t M","どぅ"=>"d M");
#
# ミクの発音用テキストに於ける初期値の設定。
#
  my @myCommonSection =();
  push @myCommonSection, "[Common]";
  push @myCommonSection, "Version=DSB301";
  push @myCommonSection, "Name=Voice1";
  push @myCommonSection, "Color=181,162,123";
  push @myCommonSection, "DynamicsMode=1";
  push @myCommonSection, "PlayMode=1";

  my @myMasterSection =();
  push @myMasterSection, "[Master]";
  push @myMasterSection, "PreMeasure=4";

  my @myMixerSection =();
  push @myMixerSection, "[Mixer]";
  push @myMixerSection, "MasterFeder=0";
  push @myMixerSection, "MasterPanpot=0";
  push @myMixerSection, "MasterMute=0";
  push @myMixerSection, "OutputMode=0";
  push @myMixerSection, "Tracks=1";
  push @myMixerSection, "Feder0=0";
  push @myMixerSection, "Panpot0=0";
  push @myMixerSection, "Mute0=0";
  push @myMixerSection, "Solo0=0";

  my @myEventListSection =();
  push @myEventListSection, "[EventList]";
  push @myEventListSection, "0=ID#0000";

  my @myIDSection =();
  push @myIDSection, "[ID#0000]";
  push @myIDSection, "Type=Singer";
  push @myIDSection, "IconHandle=h#0000";

  my @myHandleSection =();
  push @myHandleSection, "[h#0000]";
  push @myHandleSection, "IconID=\$07010000";
  push @myHandleSection, "IDS=Miku";
  push @myHandleSection, "Original=0";
  push @myHandleSection, "Caption=";
  push @myHandleSection, "Length=1";
  push @myHandleSection, "Language=0";
  push @myHandleSection, "Program=0";
my @mikuMidiEvents = ();
  push @mikuMidiEvents,['control_change' , 0, 0,  99, 96];
  push @mikuMidiEvents,['control_change' , 0, 0,  98,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,   6,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,  38,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,  98,  1];
  push @mikuMidiEvents,['control_change' , 0, 0,   6,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,  38,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,  98,  2];
  push @mikuMidiEvents,['control_change' , 0, 0,   6,  0];
  push @mikuMidiEvents,['control_change' , 0, 0,  99, 83];
  push @mikuMidiEvents,['control_change' , 0, 0,  98,  2];
  push @mikuMidiEvents,['control_change' , 0, 0,   6,  0];

#
# ミク発音(平仮名)を、ミク発音用メタデータに変換し、
#  同時にMIDIイベントを生成する。
#
  my $i=0;
  my $idxLyric = 0;
  my $pitch = 240;
  my $note = 64;
  for($i=0; $idxLyric<length($myStr2Talk); $i++ ) {
    my $myLyricLen = 6;
    my $myLyric = "";
    my $myPhonetic = "";
    for($myLyricLen=6; $myLyricLen>0; $myLyricLen-=2) {
      $myLyric = substr($myStr2Talk,$idxLyric,$myLyricLen);
      $myPhonetic = $phonetic{$myLyric};
      if( defined($myPhonetic) || $myLyricLen==2 ) {
        last;
      }
    }
    $idxLyric += $myLyricLen;

    if( defined($myPhonetic)) {
      push @myEventListSection, sprintf("%d=ID#%04d",$i*$pitch+7680,$i+1);
      push @myIDSection, sprintf("[ID#%04d]",$i+1);
      push @myIDSection, "Type=Anote";
      push @myIDSection, "Length=".$pitch;
      push @myIDSection, "Note#=".$note;
      push @myIDSection, "Dynamics=64";
      push @myIDSection, "PMBendDepth=20";
      push @myIDSection, "PMBendLength=0";
      push @myIDSection, "PMbPortamentoUse=0";
      push @myIDSection, "DEMdecGainRate=50";
      push @myIDSection, "DEMaccent=50";
      push @myIDSection, sprintf("LyricHandle=h#%04d",$i+1);
 
      push @myHandleSection, sprintf("[h#%04d]",$i+1);
      push @myHandleSection, "L0=\"".$myLyric."\",\"". $myPhonetic."\",1.000000,64,0,0";
    }
    if( $i==0 ) {
      push @mikuMidiEvents,['control_change', 5760, 0, 99,  80];
    } else {
      push @mikuMidiEvents,['control_change', $pitch, 0, 99,  80];
    }
    push @mikuMidiEvents,['control_change', 0, 0, 98,   0];
    push @mikuMidiEvents,['control_change', 0, 0,  6,   0];
    push @mikuMidiEvents,['control_change', 0, 0, 38,   0];
    push @mikuMidiEvents,['control_change', 0, 0, 98,   1];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  15];
    push @mikuMidiEvents,['control_change', 0, 0, 38,  80];
    push @mikuMidiEvents,['control_change', 0, 0, 98,   2];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  64];
    push @mikuMidiEvents,['control_change', 0, 0, 98,   3];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  64];
    push @mikuMidiEvents,['control_change', 0, 0, 98,   4];
    push @mikuMidiEvents,['control_change', 0, 0,  6,   1];
    push @mikuMidiEvents,['control_change', 0, 0, 38, 122];
    push @mikuMidiEvents,['control_change', 0, 0, 98,   5];
    push @mikuMidiEvents,['control_change', 0, 0,  6,   1];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  18];
    push @mikuMidiEvents,['control_change', 0, 0,  6,   3];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  19];
    push @mikuMidiEvents,['control_change', 0, 0,  6, 109];
    push @mikuMidiEvents,['control_change', 0, 0, 38,  64];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  20];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  39];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  21];
    push @mikuMidiEvents,['control_change', 0, 0,  6, 105];
    push @mikuMidiEvents,['control_change', 0, 0, 38,   0];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  79];
    push @mikuMidiEvents,['control_change', 0, 0,  6, 127];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  80];
    push @mikuMidiEvents,['control_change', 0, 0, 6,   12];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  81];
    push @mikuMidiEvents,['control_change', 0, 0,  6,   8];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  82];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  20];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  83];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  28];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  84];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  24];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  85];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  10];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  86];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  12];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  87];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  12];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  88];
    push @mikuMidiEvents,['control_change', 0, 0,  6,   0];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  89];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  50];
    push @mikuMidiEvents,['control_change', 0, 0, 98,  90];
    push @mikuMidiEvents,['control_change', 0, 0,  6,  50];
    push @mikuMidiEvents,['control_change', 0, 0, 98, 127];
    push @mikuMidiEvents,['control_change', 0, 0,  6, 127];
  }
  push @mikuMidiEvents,['end_track' , $pitch+1920];
  push @myEventListSection, sprintf("%d=EOS",$i*$pitch+7620);
#
#  ミク発音用メタデータのセクションを結合する
#
  my $my_miku_phonetics="";
  my $phonetic = "";
  foreach $phonetic (@myCommonSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myMasterSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myMixerSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myEventListSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myIDSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  foreach $phonetic (@myHandleSection) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
#
#  Voice1トラックを生成する。
#
my @voice1Events = (
  ['track_name',    0, 'Voice1'],
);
  for($i=0; $i*119<length($my_miku_phonetics); $i++) {
    push @voice1Events, ['text_event', 0,
      sprintf("DM:%04d:",$i).substr($my_miku_phonetics,$i*119,119) ];
  }
  my $mikuMidi = "";
  foreach $mikuMidi (@mikuMidiEvents) {
    push @voice1Events,$mikuMidi;
  }
#
# マスタートラックとVoice1トラックからVSQファイルを生成する。
#
  my $master_track = MIDI::Track->new({ 'events' => \@masterEvents });
  my $voice1_track = MIDI::Track->new({ 'events' => \@voice1Events });
  my $opus = MIDI::Opus->new(
    { 'format' => 1, 'ticks' => 480, 'tracks' => [ $master_track, $voice1_track ] } );
  $opus->write_to_file( $myVsqFile );
}

| | コメント (0) | トラックバック (0)

CVシリーズ Vocal CD Volume 01 星のカケラ

「初音ミク」の公認デビューCDが発売されるようですね。広告リンクはこちらです。

CVシリーズ Vocal CD Volume 01 星のカケラ/初音ミク
http://www.animate.tv/pv/detail.php?id=pcd071211a
発売日:2008/1/25
価格:2,000円(税込)
発売元:株式会社フロンティアワークス

 最初のフレーズのみのサンプル音声を視聴すると、流石と思わせる出来栄えでした。恐らく購入する事になると思います。
 他に収録されることになる「納得のカバーソング」ってどんな曲でしょう。「奇跡の海」とかだったらちょっと面白いんですけれど。

| | コメント (0) | トラックバック (0)

初音ミクに喋らせてみた(Perl版)

まだ、ハードコーディング段階ですが、とりあえず Perl スクリプトで .VSQ を自動生成してみました。
必要なものは ActivePerl 5.8.8 と MIDI-Perlだけです。ActivePerl をインストールしたのち、ppm-shell を起動して MIDI-Perl をインストールしてください。

 こちらが、「みく」と喋るVSQファイルを生成する Perlスクリプトです。
 「miku_talk001.zip」をダウンロード

 こちらが、その生成されたVSQファイルです。
 「test_miku.zip」をダウンロード

流石に「みく」の決めうちじゃあさびしいので、せめて任意の平仮名入力をVSQ変換したいと思い、VOCALOID2 の平仮名→発音記号テーブルをちょっと見てみたら、世の中にはもう調べ終わっている人がいるものですね。こちらの方です。

初心者になるための耳コピMIDI講座 マニュアル (VSTi)
VOCALOID2 Domino 定義ファイル
http://mimikopi.nomaki.jp/domino/vocaloid2/manual/index.html#HEADER

恥を忍んでソースをご紹介します。いや・・・、今日1時間ほどで作ったものなんで汚いのはご容赦ください。

#!/Perl
#
#  miku_talk ver.0.0.1
#
#  Programmed by Akira Izumi 6/Dec/2007
#
use MIDI;
use strict;
use warnings;

my $myTalk = "みく";
my $miku_talk_metatext = miku_phonetics($myTalk);

my @masterEvents = (
  ['text_event',    0, 'Master Track'],
  ['set_tempo',     0, 500_000], # 1qn = .50 seconds
  ['time_signature',0,4,2,24,8 ],
  ['end_track' ,    0],
);

  my @voice1Events = (
    ['text_event',    0, 'Voice1'],
  );
  my $i=0;
  for($i=0; $i*119<length($miku_talk_metatext); $i++) {
    push @voice1Events, ['text_event', 0, sprintf("DM:%04d:",$i).substr($miku_talk_metatext,$i*119,119) ];
  }
  push @voice1Events,['control_change' , 0, 0,  99, 96];
  push @voice1Events,['control_change' , 0, 0,  98,  0];
  push @voice1Events,['control_change' , 0, 0,   6,  0];
  push @voice1Events,['control_change' , 0, 0,  38,  0];
  push @voice1Events,['control_change' , 0, 0,  98,  1];
  push @voice1Events,['control_change' , 0, 0,   6,  0];
  push @voice1Events,['control_change' , 0, 0,  38,  0];
  push @voice1Events,['control_change' , 0, 0,  98,  2];
  push @voice1Events,['control_change' , 0, 0,   6,  0];
  push @voice1Events,['control_change' , 0, 0,  99, 83];
  push @voice1Events,['control_change' , 0, 0,  98,  2];
  push @voice1Events,['control_change' , 0, 0,   6,  0];

  push @voice1Events,['control_change', 5760, 0, 99,  80];
  push @voice1Events,['control_change', 0, 0, 98,   0];
  push @voice1Events,['control_change', 0, 0,  6,   0];
  push @voice1Events,['control_change', 0, 0, 38,   0];
  push @voice1Events,['control_change', 0, 0, 98,   1];
  push @voice1Events,['control_change', 0, 0,  6,  15];
  push @voice1Events,['control_change', 0, 0, 38,  80];
  push @voice1Events,['control_change', 0, 0, 98,   2];
  push @voice1Events,['control_change', 0, 0,  6,  64];
  push @voice1Events,['control_change', 0, 0, 98,   3];
  push @voice1Events,['control_change', 0, 0,  6,  64];
  push @voice1Events,['control_change', 0, 0, 98,   4];
  push @voice1Events,['control_change', 0, 0,  6,   1];
  push @voice1Events,['control_change', 0, 0, 38, 122];
  push @voice1Events,['control_change', 0, 0, 98,   5];
  push @voice1Events,['control_change', 0, 0,  6,   1];
  push @voice1Events,['control_change', 0, 0, 98,  18];
  push @voice1Events,['control_change', 0, 0,  6,   3];
  push @voice1Events,['control_change', 0, 0, 98,  19];
  push @voice1Events,['control_change', 0, 0,  6, 109];
  push @voice1Events,['control_change', 0, 0, 38,  64];
  push @voice1Events,['control_change', 0, 0, 98,  20];
  push @voice1Events,['control_change', 0, 0,  6,  39];
  push @voice1Events,['control_change', 0, 0, 98,  21];
  push @voice1Events,['control_change', 0, 0,  6, 105];
  push @voice1Events,['control_change', 0, 0, 38,   0];
  push @voice1Events,['control_change', 0, 0, 98,  79];
  push @voice1Events,['control_change', 0, 0,  6, 127];
  push @voice1Events,['control_change', 0, 0, 98,  80];
  push @voice1Events,['control_change', 0, 0, 6,   12];
  push @voice1Events,['control_change', 0, 0, 98,  81];
  push @voice1Events,['control_change', 0, 0,  6,   8];
  push @voice1Events,['control_change', 0, 0, 98,  82];
  push @voice1Events,['control_change', 0, 0,  6,  20];
  push @voice1Events,['control_change', 0, 0, 98,  83];
  push @voice1Events,['control_change', 0, 0,  6,  28];
  push @voice1Events,['control_change', 0, 0, 98,  84];
  push @voice1Events,['control_change', 0, 0,  6,  24];
  push @voice1Events,['control_change', 0, 0, 98,  85];
  push @voice1Events,['control_change', 0, 0,  6,  10];
  push @voice1Events,['control_change', 0, 0, 98,  86];
  push @voice1Events,['control_change', 0, 0,  6,  12];
  push @voice1Events,['control_change', 0, 0, 98,  87];
  push @voice1Events,['control_change', 0, 0,  6,  12];
  push @voice1Events,['control_change', 0, 0, 98,  88];
  push @voice1Events,['control_change', 0, 0,  6,   0];
  push @voice1Events,['control_change', 0, 0, 98,  89];
  push @voice1Events,['control_change', 0, 0,  6,  50];
  push @voice1Events,['control_change', 0, 0, 98,  90];
  push @voice1Events,['control_change', 0, 0,  6,  50];
  push @voice1Events,['control_change', 0, 0, 98, 127];
  push @voice1Events,['control_change', 0, 0,  6, 127];

  push @voice1Events,['end_track' , 2160];

  my $master_track = MIDI::Track->new({ 'events' => \@masterEvents });
  my $voice1_track = MIDI::Track->new({ 'events' => \@voice1Events });
  my $opus = MIDI::Opus->new(
    { 'format' => 1, 'ticks' => 480, 'tracks' => [ $master_track, $voice1_track ] } );
  $opus->write_to_file( 'test_miku.vsq' );
  exit(0);
#-----------------------------------------------------------------------
#
#  ミクの発音用メタテキスト
#
sub miku_phonetics {

my @myPhonetics=();

  push @myPhonetics, "[Common]";
  push @myPhonetics, "Version=DSB301";
push @myPhonetics, "Name=Voice1";
push @myPhonetics, "Color=181,162,123";
push @myPhonetics, "DynamicsMode=1";
push @myPhonetics, "PlayMode=1";

push @myPhonetics, "[Master]";
push @myPhonetics, "PreMeasure=4";

push @myPhonetics, "[Mixer]";
push @myPhonetics, "MasterFeder=0";
push @myPhonetics, "MasterPanpot=0";
push @myPhonetics, "MasterMute=0";
push @myPhonetics, "OutputMode=0";
push @myPhonetics, "Tracks=1";
push @myPhonetics, "Feder0=0";
push @myPhonetics, "Panpot0=0";
push @myPhonetics, "Mute0=0";
push @myPhonetics, "Solo0=0";

push @myPhonetics, "[EventList]";
push @myPhonetics, "0=ID#0000";
push @myPhonetics, "7680=ID#0001";
push @myPhonetics, "7920=ID#0002";
push @myPhonetics, "8160=EOS";

push @myPhonetics, "[ID#0000]";
push @myPhonetics, "Type=Singer";
push @myPhonetics, "IconHandle=h#0000";

push @myPhonetics, "[ID#0001]";
push @myPhonetics, "Type=Anote";
push @myPhonetics, "Length=240";
push @myPhonetics, "Note#=64";
push @myPhonetics, "Dynamics=64";
push @myPhonetics, "PMBendDepth=20";
push @myPhonetics, "PMBendLength=0";
push @myPhonetics, "PMbPortamentoUse=0";
push @myPhonetics, "DEMdecGainRate=50";
push @myPhonetics, "DEMaccent=50";
push @myPhonetics, "LyricHandle=h#0001";

push @myPhonetics, "[ID#0002]";
push @myPhonetics, "Type=Anote";
push @myPhonetics, "Length=240";
push @myPhonetics, "Note#=64";
push @myPhonetics, "Dynamics=64";
push @myPhonetics, "PMBendDepth=20";
push @myPhonetics, "PMBendLength=0";
push @myPhonetics, "PMbPortamentoUse=0";
push @myPhonetics, "DEMdecGainRate=50";
push @myPhonetics, "DEMaccent=50";
push @myPhonetics, "LyricHandle=h#0002";

push @myPhonetics, "[h#0000]";
push @myPhonetics, "IconID=\$07010000";
push @myPhonetics, "IDS=Miku";
push @myPhonetics, "Original=0";
push @myPhonetics, "Caption=";
push @myPhonetics, "Length=1";
push @myPhonetics, "Language=0";
push @myPhonetics, "Program=0";

push @myPhonetics, "[h#0001]";
push @myPhonetics, "L0=\"み\",\"m' i\",1.000000,64,0,0";

  push @myPhonetics, "[h#0002]";
  push @myPhonetics, "L0=\"く\",\"k M\",1.000000,64,0,0";

  my $my_miku_phonetics="";
  my $phonetic = "";
  foreach $phonetic (@myPhonetics) {
    $my_miku_phonetics = $my_miku_phonetics.$phonetic."\n";
  }
  return $my_miku_phonetics;
}


| | コメント (2) | トラックバック (1)

CV02「鏡音リン・レン」

大手広告代理店のティザー広告も顔負け!

DTMマガジン12月号(11月8日)にCV02 鏡音リンの画像を発表すると同時に、メディアファージ事業部ブログでも発表、鏡音リンのネタで一通り盛り上がったところで、いきなり「実は双子です。男女の声でボーカドイロ2が使えます!」

 [VOCALOID2情報] CV02「鏡音リン・レン」公開
 http://blog.crypton.co.jp/mp/2007/12/vocaloid2_cv02_3.html

 クリプトン VOCALOID2特集 鏡音リン・レン(カガミネ リン・レン) 紹介ページ更新
 http://www.crypton.co.jp/mp/pages/prod/vocaloid/cv02.jsp

この展開を考えた人(恐らくCrypton社のwatさんと思いますが、)は天才的なプロモーターと思います。自分はCV02は買わないと決めていましたが、その決心は相当ぐらついています。

ところで、CV02を買うその前に、Midi::Perl の仕様書をちゃんと読みこなさないといけませんね。(笑)

| | コメント (0) | トラックバック (0)

VOCALOIDのデータ形式

ここにも、VOCALOID2 Editor のデータ形式をチェックされている方がおられました。

VOCALOID MIDI 形式
http://cancoffee2.at.webry.info/200711/article_8.html

今日はMecabのインストールでちょと苦労しました。
Yahoo! の形態素解析WEB-APIは「プライベート文書」を変換するには危険すぎますので、MeCabという名の形態素解析エンジンをインストールしました。お約束の特許法2条1項の文章を解析した結果は以下のものです。

発明    名詞,サ変接続,*,*,*,*,発明,ハツメイ,ハツメイ
と    助詞,格助詞,引用,*,*,*,と,ト,ト
は    助詞,係助詞,*,*,*,*,は,ハ,ワ
、    記号,読点,*,*,*,*,、,、,、
自然    名詞,形容動詞語幹,*,*,*,*,自然,シゼン,シゼン
法則    名詞,一般,*,*,*,*,法則,ホウソク,ホーソク
を    助詞,格助詞,一般,*,*,*,を,ヲ,ヲ
利用    名詞,サ変接続,*,*,*,*,利用,リヨウ,リヨー
し    動詞,自立,*,*,サ変・スル,連用形,する,シ,シ
た    助動詞,*,*,*,特殊・タ,基本形,た,タ,タ
技術    名詞,一般,*,*,*,*,技術,ギジュツ,ギジュツ
的    名詞,接尾,形容動詞語幹,*,*,*,的,テキ,テキ
思想    名詞,一般,*,*,*,*,思想,シソウ,シソー
の    助詞,連体化,*,*,*,*,の,ノ,ノ
創作    名詞,サ変接続,*,*,*,*,創作,ソウサク,ソーサク
の    助詞,連体化,*,*,*,*,の,ノ,ノ
うち    名詞,非自立,副詞可能,*,*,*,うち,ウチ,ウチ
高度    名詞,形容動詞語幹,*,*,*,*,高度,コウド,コード
な    助動詞,*,*,*,特殊・ダ,体言接続,だ,ナ,ナ
もの    名詞,非自立,一般,*,*,*,もの,モノ,モノ
を    助詞,格助詞,一般,*,*,*,を,ヲ,ヲ
いう    動詞,自立,*,*,五段・ワ行促音便,基本形,いう,イウ,イウ
。    記号,句点,*,*,*,*,。,。,。

その後、MecabをPerl から呼び出す為の Perl-binding をインストールしようとしたら、UNIXが前提になっているらしくて一苦労でしたが、ppm モジュールを公開されている方がおられましたので、そちらからインストールすることで無事に動作するようになりました。
こちらの方です。
http://namazu.asablo.jp/blog/2007/06/28/1611341

Mecab Perl-binding PPMモジュールのインストール方法は以下のものです。

C:\> ppm uninstall MeCab
C:\> ppm install http://www.akaneiro.jp/PPMPackages/800/MeCab.ppd

| | コメント (0) | トラックバック (0)

日本語のアクセント

日本語のアクセントで調べていると、Yahoo辞書に、共通語(標準語)のアクセントにかかわる記載を見つけました。以下に引用します。

『大辞林 第二版』のアクセント表示


  1. 日本語のアクセントは、単語を発音するさいに、その単語の中に含まれる個々の「拍」を高く発音するか低く発音するかによって決まる。拍とは日本語の音の長さの単位をいい、「キャ・シュ・チョ」などの拗音はカナ2字で1拍である。

  2. 共通語では、1拍目と2拍目との間に必ず音の高低の変化がある。

  3. 1拍目が高で2拍目以降が低である語は「頭高型」と言い、この辞典では [1] で示した。

  4. 1拍目が低で、あとに続く助詞を含め高から低に移る箇所のない語は「平板式」と言い [0] で示した。

  5. 1拍目が低で、2拍目以降が高になり、語中、語末に高から低に移る箇所のある語は「中高型」または「尾高型」と言い、低に移る直前の音の位置が2拍目であれば [2]、3拍目であれば [3]… のように示した。その位置が語中にあるものを「中高型」、語末にあるものを「尾高型」と言う。

  6. 以上のうち、平板式を除く「頭高型」「中高型」「尾高型」を総称して「起伏式」と言う。

 これを見ると、標準語のアクセントルールが意外と単純なことがわかります。たったこれだけのルールで構成されているのですから。
 自然文を形態素解析して単語に分解し、辞書をもとに単語のアクセントの種類を調べ、上記ルール通りのアクセントを付与すれば、初音ミクが自然文を喋るシステムが出来上がりですね。

| | コメント (2) | トラックバック (0)

ストラトスフィア

これも、初音ミクを用いたトランスのオリジナル曲です。様々な才能を持った者たちが次々と初音ミクを使いこなす様が、あたかもコンピュータが「マイコン」と呼ばれていた非力な頃に、遠い将来の可能性を見出し、従来の産業構造を変革するムーブメントを起こした天才ハッカーたちの姿とダブります。

| | コメント (0) | トラックバック (0)

初音ミクの商標登録出願

 クリプトン・フューチャー・メディア(株)さんも、「初音ミク」を商標登録出願してましたね。ちょっと気になっていたんで特許電子図書館で検索を掛けたらヒットしました。出願日は初音ミク発売日の1週間後です。 この商標は著名性が高いので、商標の価値は高いです。
 指定商品に「電子出版物」が記載されているのは流石とおもいました。初音ミクが読み上げる○○○なんていう商品もこの出願でカバーされるよう考慮されているのですからね。ただ、自分がこの出願を担当したならば、第41類「技芸、スポーツ又は知識の教授」「電子出版物の提供」も含めるとおもいます。
 CVシリーズ02「鏡音リン」で検索したらヒットしませんでしたが、こちらも既に商標登録出願されているのではないかと思います。


(210) 【出願番号】 商願2007-99911
(220) 【出願日】 平成19年(2007)9月6日
  【先願権発生日】 平成19年(2007)9月6日
  【最終処分日】
  【最終処分種別】  
  【出願種別】                                        

  【商標(検索用)】 初音ミク
(541) 【標準文字商標】 初音ミク
(561) 【称呼】 ハツネミク
(531) 【ウィーン図形分類】

(731) 【出願人】
  【氏名又は名称】 クリプトン・フューチャー・メディア株式会社

  【類似群】 05D01 09A01 09D01 09E21 09E26 09G53 19B33 24A01 24B02 24C01 24D01 24E01 25B02 26A01 26D01 41E01 41E02 41E03 41E04 41H01 41J01 41K01 41K02 41M01 41M06 41M08 41Z99 42G01 42N01 42N02 42N03 42P01 42P02 42P03 42Q01 42Q02 42Q03 42Q99 42R02 42R03 42X04 42X11 42X14 42X31
  【国際分類版表示】 第9版
(500) 【区分数】
(511) (512) 【商品及び役務の区分並びに指定商品又は指定役務】
移 動体電話による通信を用いてダウンロードされる移動体電話機の着信用の音楽,録画済みビデオディスク及びビデオテープ,自動販売機,駐車場用硬貨作動式 ゲート,作業記録機,写真複写機,手動計算機,製図用又は図案用の機械器具,タイムスタンプ,タイムレコーダー,電気計算機,パンチカードシステム機械, 票数計算機,ビリングマシン,郵便切手のはり付けチェック装置,ウエイトベルト,レギュレーター,家庭用テレビゲームおもちゃ,電気溶接装置,メトロノー ム,携帯用液晶画面ゲームおもちゃ用のプログラムを記憶させた電子回路及びCD―ROM,電子楽器用自動伴奏プログラムを記憶させた電子回路及び CD―ROM,電子出版物
28 スキーワックス,遊園地用機械器具(業務用テレビゲーム機を除く。),愛玩動物用おもちゃ,おもちゃ,人形,遊戯用器具,ビリヤード用具,運動用具,釣り具,昆虫採集用具
41 ゲー ム機械器具を備えた遊戯場・遊園地・その他の娯楽施設の提供,映画・演芸・演劇・音楽又は教育研修のための施設の提供,電子計算機端末による通信を用いて 行うゲーム又はゲームに関する映像の提供,ボウリング場・その他の運動施設の提供,レコード又は録音済み磁気テープの貸与,録画済み磁気テープの貸与,お もちゃの貸与,遊園地用機械器具の貸与,スロットマシンの貸与,遊戯用器具の貸与,映画・演芸・演劇又は音楽の演奏の興行の企画又は運営,映画の上映・制 作又は配給,演芸の上演,演劇の演出又は上演,音楽の演奏,放送番組の制作,音響用又は映像用のスタジオの提供,映写機及びその附属品の貸与,映写フィル ムの貸与,移動体電話による通信を用いて行うゲームの提供
42 イ ンターネット・電子メールその他の通信ネットワークを用いた電子計算機用プログラムの提供,移動体電話による電子計算機用プログラムの提供,気象情報の提 供,建築物の設計,測量,地質の調査,機械・装置若しくは器具(これらの部品を含む。)又はこれらの機械等により構成される設備の設計,デザインの考案, 電子計算機のプログラムの設計・作成又は保守,電子計算機・自動車その他その用途に応じて的確な操作をするためには高度の専門的な知識・技術又は経験を必 要とする機械の性能・操作方法等に関する紹介及び説明,医薬品・化粧品又は食品の試験・検査又は研究,建築又は都市計画に関する研究,公害の防止に関する 試験又は研究,電気に関する試験又は研究,土木に関する試験又は研究,農業・畜産又は水産に関する試験・検査又は研究,機械器具に関する試験又は研究,著 作権の利用に関する契約の代理又は媒介,社会保険に関する手続きの代理,計測器の貸与,電子計算機の貸与,電子計算機用プログラムの提供,理化学機械器具 の貸与,製図用具の貸与

| | コメント (0) | トラックバック (2)

初音ミクと著作権について #2

 先日、当該ブログに書いた「初音ミクと著作権について」の追記です。
 松尾公也さんのブログに「初音ミクが問いかける、楽器と歌手の境界線」で、幾つかの問題を提起されています。初音ミクを用いた音楽は「歌唱」なのか否か、「歌唱」と判断するならば、どの程度の「歌声度」ならば「歌唱」と判断し、それ以外を「楽器」と判断するのかという点です。
 現実に松尾さんが初音ミクに歌わせた歌はMySoundユーザースペースに公開申請しても手続きに手間取っているようで、MySoundユーザースペース運営元のYAMAHAと著作権申請先のJASRACの両者で喧々諤々と議論されているのではないかと想像します。
 以下に自分の意見を述べます。

◆初音ミクを用いた音楽は歌唱なのか否か?

 著作権法、及びJASRACの使用料規定には歌唱は定義されていません。大辞林 第二版 (三省堂)には以下のように定義されています。

かしょう ―しやう 【歌唱】

(名)スル

歌をうたうこと。また、歌。
「―の指導」「―力」

 この定義に歌唱の主体は明示されていませんが、暗黙のうちに自然人が想定されていると解されます。よって、VOCALOID2 Editor がWAVファイルを出力することは歌唱には該当しません。主体が自然人ではないからです。
 しかし、初音ミクを用いた音楽の固定物は「歌唱の固定物」と判断します。その理由は、VOCALOID Editor 入力者が、その歌唱の固定物を得たいという意思のもとに入力をおこなっている事によります。これは、結果の発生を認識しながらそれを容認して行為するという心理状態に該当し、民法上の故意と判断されます。(故意-Wikipedia より) また、客観的に、その歌詞及び音階で聞き取れる場合には、原歌詞の歌唱の固定物を故意に作成したと主張することは容易とおもいます。

 しかし、これにはやはり疑義あると思います。実際には歌詞通りにVOCALOID Editor に打ち込むことはなく、発音を自然にjする為、多少のアレンジを加えるからです。例えば、「はつめい」を「はつめー」「とっきょ」を「と<無発音>きょ」等とアレンジすることがこれに該当します。このようなアレンジを加えていって、原曲の歌詞と相違する歌唱をVOCALOID Editor で入力した場合にはどう判断すべきかは極めて微妙と思います。

 また、松尾さんの例では、初音ミクに適当なハミング、『タララララー』とか『ファファファファファ~』などで歌わせて公開申請したそうです。JASRAC がどう判断するのか興味深いです。自分は、この初音ミクのハミングは歌唱ではあるが原作詞家の上演権(著作権法22条)の権利範囲には入らず、作曲家の演奏権(著作権法22条)の権利範囲のみに入ると判断します。

◆どの程度の「歌声度」ならば「歌唱」と判断し、それ以外を「楽器」と判断するのか?
 著作権法上、歌唱と楽器は定義されておらず、法上の判断基準はありません。寡聞にして判例や通説も知りません。よって判断基準は不明です。
 あえて基準を想定するならば、以下のようなものが考えられます。

①一部の視聴者が楽曲中に歌詞を聞き取れたならば、歌唱と判断する。
②大部分の視聴者が楽曲中に歌詞を明確に聞き取れたならば、歌唱と判断する。
③一部の視聴者がブラインドテストで人間の歌唱と区別つかなかったならば歌唱と判断する。
④大部分の視聴者がブラインドテストで人間の歌唱と区別つかなかったならば歌唱と判断する。

 ①と②の判断基準は、著作権法2条1項3号の実演の要件「演劇的に歌い」の要件を満たさないと解され、これが基準となるとは思えません。よって、③または④が基準となると思われ、自分としては④が要件となると予想しています。
 どの歌唱合成装置を用いたかは本質的ではありませんが、PC-6001やPLG100-SGなどの音声合成の品質は③又は④の要件を満たすとは思えません。実務的には YAMAHA の VOCALOIDシリーズまたはそれと同等以上の音声品質を具備した製品に限定されると思います。

余談ですが、上記判断基準はチューリングテストに似ていると思ってしまいました。

チューリング・テスト (Turing test) とは、アラン・チューリングによって考案された、ある機械が知的かどうか(人工知能であるかどうか)を判定するためのテスト。チューリングテストを機械が意識しているか、機械が理解しているかの基準とする考えもある。

Wikipedia より

| | コメント (2) | トラックバック (0)

涙にさよなら

次にご紹介する「涙にさよなら」は、初音ミクのキャラクターソングではなく、通常のJPOPです。曲、歌詞、そして画像も文句のつけようがなく、恐らくプロ又はセミプロの方が作られたのではないかと想像します。

ここまで自然な言葉遣いにするまで、どれだけのカット&トライをおこなったのでしょうか。また、「初音ミク」というキャラクターを離れて通常のJPOPに使用できるということが、この曲によって示されたとおもいます。

| | コメント (0) | トラックバック (0)

Yahoo!の形態素解析

先日ご紹介した Yahoo!の日本語形態素解析WebサービスをPerlから叩いてみました。
サンプルプログラムはケーズメモさんのブログにアップされています。
Yahoo!の形態素解析を利用してみた by Perl
 殆ど完璧なサンプルで、モジュールをうまく活用して極めて短くシンプルに仕上がっています。デフォルト状態だとYAMLモジュールが無いことに起因するエラーが表示されるので、コマンドラインから ppm を起動して、install YAML を入力してください。
 あと、ソースコードは UTF-8 であることが前提となっています。うっかりS-JISで保存したら、解析結果が化け化けになってしまいました。ご注意ください。
 お約束の特許法2条1項 「発明とは、自然法則を利用した技術的思想の創作のうち高度なものをいう。」を形態素解析した結果はこちらです。

---
ma_result:
  filtered_count: 23
  total_count: 23
  word_list:
    word:
      - pos: 名詞
        reading: はつめい
        surface: 発明
      - pos: 助詞
        reading: と
        surface: と
      - pos: 助詞
        reading: は
        surface: は
      - pos: 特殊
        reading: 、
        surface: 、
      - pos: 名詞
        reading: しぜん
        surface: 自然
      - pos: 名詞
        reading: ほうそく
        surface: 法則
      - pos: 助詞
        reading: を
        surface: を
      - pos: 名詞
        reading: りよう
        surface: 利用
      - pos: 助動詞
        reading: し
        surface: し
      - pos: 助動詞
        reading: た
        surface: た
      - pos: 名詞
        reading: ぎじゅつ
        surface: 技術
      - pos: 接尾辞
        reading: てき
        surface: 的
      - pos: 名詞
        reading: しそう
        surface: 思想
      - pos: 助詞
        reading: の
        surface: の
      - pos: 名詞
        reading: そうさく
        surface: 創作
      - pos: 助詞
        reading: の
        surface: の
      - pos: 名詞
        reading: うち
        surface: うち
      - pos: 名詞
        reading: こうど
        surface: 高度
      - pos: 助動詞
        reading: な
        surface: な
      - pos: 名詞
        reading: もの
        surface: もの
      - pos: 助詞
        reading: を
        surface: を
      - pos: 動詞
        reading: いう
        surface: いう
      - pos: 特殊
        reading: 。
        surface: 。
xmlns: urn:yahoo:jp:jlp
xmlns:xsi: http://www.w3.org/2001/XMLSchema-instance
xsi:schemaLocation: urn:yahoo:jp:jlp http://api.jlp.yahoo.co.jp/MAService/V1/parseResponse.xsd

 XMLファイルはこちらです。【「hatumei.xml」をダウンロード
 読み仮名の情報はそのまま入っているので使えそうです。文節情報は、品詞情報をもとに再構築する必要があるかと思います。
 これで chasen と辞書のインストールなしに形態素解析ができましたので、次は形態素解析した結果をもとに .VSQ ファイルを自動生成させたく思います。

| | コメント (0) | トラックバック (0)

DTMマガジン増刊CV01初音ミク

備忘録のために購入予定商品を貼り。


今日、初音ミクのソフト本体を注文。DTMマガジン11月号添付のデモでは、プロジェクトを保存できないから、このままではプロジェクトファイル (.VSQ) の解析すらできないためです。

AMAZON で注文したら一割引なので、ちょっと特をした気分です。昨日ビックカメラのDTMコーナーで売られているのを見たが、定価販売でした。「ポイントカードがあるからいいでしょ」という趣旨かな。


| | コメント (0) | トラックバック (1)

特許法29条1項柱書の試作品

特許法29条1項柱書を初音ミクに喋らせてみました。まだ試作品ですので、音階とピッチを含めて全部手で打っていますが、将来的には Perl スクリプトでVSQファイルを自動生成する予定です。
自然文の形態素解析は最初 Mecabを使おうかと思っていましたが、Yahooの形態素解析WEBサービスの方が楽そうです。

「特許法29条」をダウンロード

前回の試作品よりも少しだけ自然な喋りに近づけたのではないかと思います。備忘録として以下に喋りの技術を記載します。

◆「とっきょほう」の促音の「っ」について

促音の「っ」を直接に入力すると、有声子音で発音し、発音が強すぎて不自然になります。PHONETIC(発音記号)に "ts M" と表記されている末尾の M を削除すると、無声子音になり、自然な発音となります。

Hatuon_tsu
図1、無声子音の「っ」

◆アクセントについて
①基本的なアクセント
基本は2音階でおこないます。

②アクセントと単語と文脈の関連性
アクセントは単語のみでは決まらず、文頭か文中かでも相違するようです。例えば「とっきょ」ですが、文頭では「とっ/きょ」と音階を上げ、文中では「とっ\きょ」と音階を下げています。標準語の発音では、直前の音階に依存して、音階の上げ下げが決まるするのかもしれません。まだこの点では調査を要します。

Tokkyohou_top_4    

図2、文頭における「とっ/きょ」の発音

Tokkyo_middle

図3、文中における「とっ\きょ」の発音

③音階の自己調整
喋り始めの1文節と、それ以降の文節で微妙に音階を変えると人間っぽくなりました。人間も最初の一文節で音階の自己調節をおこない、最適な音階に再設定して、それ以降の文節を発音しているのではないかと思います。

◆ピッチについて
ピッチは、強調したい部分である名詞を4/32で、それ以外の代名詞、動詞、形容詞、副詞、助詞等を3/32としました。人間が文章を発音するときも同様に、重要と思う部分をゆっくりと、そうでない部分を早く発音していると考えたからです。
これにより重要キーワードを音でマーキング可能となるという副次的な効果が生まれるとおもいます。

◆ブレス音について
文章の区切りの部分である「、」と「。」の部分にブレス音(息継ぎ音)を入れました。人間の喋りを模倣し、自然に感じるようにするためです。
ブレス音の入力は、PHONETIC(発音記号)に、br1,br2,br3,br4,br5 いずれかを記載します。

Miku_breath

図4、初音ミクのブレス音

| | コメント (0) | トラックバック (0)

特許法2条1項の試作品

 やっと時間が取れたので、DTMマガジンの初音ミク体験版で「特許法の読み上げ」を試作してみました。用いた文章は特許法2条1項「発明とは、自然法則を利用した技術的思想の創作のうち高度のものをいう。」です。

「特許法2条1項」をダウンロード

 文節を発音で表現するのは割りと簡単で、文節の区切りに発音の区切りを入れればよいだけです。
 ちょっとした工夫ですが、「はつめい」ではなく「はつめー」と伸ばした方が自然に感じます。どのようなルールで直前の音を伸ばせばよいか考えて見ます。

 

しかし、アクセントは難しいですね。「君はどこの人なんだかはっきりしなさい。」という感じで、京阪のアクセントなんだか標準語のアクセントなんだか判らない感じになってしまいます。なんでも標準語のアクセントの方が単純明快で、3つのルールしか無いそうですので、その3つのルールと単語の関係をチェックしてみます。

次に掲げるのが構想メモです、形態素分析ツールを用いて日本語の自然文を品詞分解し、アクセントテーブルを介して、それぞれの発音、音階及び制御情報を付与してVSQファイルを作成したのちVOCALOID ENGINEで当該VSQファイルを読み込んで合成音声を出力し、アクセント付の読み上げ音声を得ることとします。
Miku_kousou

最終的には、テキスト画像スクロールの動画と同期させたのち、iPodに転送できればと思います。次のメモは「はちゅねみく」がネギで読み上げ部分を指し示している図です。
Miku_memo

| | コメント (2) | トラックバック (0)

初音ミクと著作権について

初音ミクと著作権について書かれているサイトをご紹介します。

(1)初音ミク 著作権を根底から脅かす恐ろしい娘

(2)初音ミク」と著作権法

(3)ピリ辛著作権相談室:バーチャルアイドルに自作の歌を歌わせたいのですが

これらの意見を見て色々と考えさせられました。
ニコニコ動画にアップロードされている「初音ミクが歌うXXXXX」とは、果たして実演の固定物なのか。実演だとしたらその主体は誰なのか。実演家の権利は発生しているのか。初音ミクが既成曲を歌った場合には、誰の権利を侵害することになるのか、侵害の主体は誰なのか。
これらを法的に検討してみます。

◆初音ミクによる楽曲は実演の固定物なのか?

まず(1)と(2)のサイトで触れられている「歌唱権」ですが、著作権法には法定されておらず、産業界にて暗黙のうちに運用されている用語のようです。著作権法上、歌唱は2条1項3号「実演」で定義されている行為に包含されます。

著作権法

第二条  この法律において、次の各号に掲げる用語の意義は、当該各号に定めるところによる。

 実演 著作物を、演劇的に演じ、舞い、演奏し、歌い、口演し、朗詠し、又はその他の方法により演ずること(これらに類する行為で、著作物を演じないが芸能的な性質を有するものを含む。)をいう。

著作権法上の「実演」は例示列挙されており、自然人が歌うことのみならず、その他の方法により演ずることを含むとされています。初音ミクが歌うことのみならず、ソフトウエアの「初音ミク」に対して音声および音階を入力する作業を実演の対象として考えるとよいかと思います。自分は、初音ミクが歌をWAVファイルに出力することが「歌う」に該当するかは判断できませんが、少なくとも初音ミクのピアノロール・エディタに音階、歌詞若しくはイフェクトを打ち込む作業は「その他の方法により演ずること」に含まれると解します。よって、初音ミクによる楽曲は実演の固定物であると判断します。
ただ、これは疑義あると思いますので、明確に法定されることが望ましいとおもいます。

なお、藤田咲さんが「初音ミク」の声の素材データを提供する行為は、50音を様々な音階で読み上げる事であると聞いております。この行為は「演劇的に歌い」の要件を満たさず、ここでいう実演には該当しないと介されます。

◆初音ミクの実演の主体は誰なのか?実演家の権利は発生しているのか?

歌唱の主体は実演家であり、次のように定義されています。

著作権法
第二条    この法律において、次の各号に掲げる用語の意義は、当該各号に定めるところによる。  

 実演家 俳優、舞踊家、演奏家、歌手その他実演を行なう者及び実演を指揮し、又は演出する者をいう。 

つまり、歌手がコンピュータによるプログラムであり、権利能力を有する自然人に該当しないとしても。そのコンピュータを用いて「その他実演を行う者」または「実演を指揮し、又は演出する者」が自然人若しくは法人であるならば、その者が実演家と解され、実演家に認められている以下の権利が発生していると解します。

①氏名表示権(著作権法90条の2)
②同一性保持権(著作権法90条の3)
③録音及び録画権(著作権法91条)
④放送権及び有線放送権(著作権法92条)
⑤送信可能化権(著作権法92条の2)
⑥放送のための固定(著作権法93条)
⑦放送のための固定物等による放送(著作権法94条)
⑧商業用レコードの二次利用(著作権法95条)
⑨譲渡権(著作権法95条の2)
⑩貸与権(著作権法95条の3)

なお、声優の藤田咲さんは初音ミクの声の素材データを提供したのみであり、「演劇的に歌う」(2条3項1号)の要件を満たしません。よって実演に該当しないために藤田咲さんは実演家ではないと判断されます。

◆初音ミクが既成曲を歌った場合、誰の権利を侵害することになるのか?侵害の主体は誰なのか?

著作権法22条に規定されている上演権又は演奏権を侵害すると判断します。ここで上演とは歌唱を含む概念です。すなわち、当該既成曲の作詞家および作曲家の権利侵害となります。侵害の主体は実演家で、すなわち初音ミクに既成曲を打ち込んだ者となると解されます。権原なく実演をおこなった為です。

もちろん、オリジナル曲を作成して初音ミクに歌わせた者は、その者が作詞家・作曲家かつ実演家となり、上演権と演奏権と実演家の権利を有しますので、第三者の権利侵害を構成しません。

第二十二条  著作者は、その著作物を、公衆に直接見せ又は聞かせることを目的として(以下「公に」という。)上演し、又は演奏する権利を専有する。

◆法改正の予言
将来的には、著作権法2条1項3号は以下の下線部が追加される事になると判断します。平成14年度の特許法等の法改正で、プログラム等が物に含まれることになったのと趣旨が似ているように思いました。

著作権法

第二条  この法律において、次の各号に掲げる用語の意義は、当該各号に定めるところによる。

 実演 著作物を、演劇的に演じ、舞い、演奏し、歌い、口演し、朗詠し、又はその他の方法により演ずること(これらに類する行為で、著作物を演じないが芸能的な性質を有するもの、若しくは歌唱合成装置による歌唱を入力する行為を含む)をいう。

余談ですが、「初音ミク・・・恐ろしい娘」という言葉を見て、ガラスの仮面の月影先生の台詞を思い出してしまいました。このキャッチコピーはアキバの店のPOPにも描かれていたそうです。

| | コメント (2) | トラックバック (1)

初音ミク・シーケンスファイルの形式

もう既に 初音ミクのシーケンスファイルを解析されている方もいます。
Vocaloidファイルから口パク用情報を取り出すツール:Rev 0.20
この口パク情報ファイルを使って、動画と自動リップシンクすれば、あら、あなたも簡単プロモーションビデオが出来てしまう・・・かもしれない。
現在は、あちこちのサイトに落ちている.初音ミクのシーケンスファイル(VSQ ファイル)をこのツールに喰わせて、色々と内部構造を推定中です。

ところで、初音ミクのシーケンスファイル形式(VSQファイル形式)の元ネタはSMF形式=標準MIDI形式なのですね。SMAF形式ではと推定したのは微妙に違っていたので残念です。なお、MIDI仕様書は太郎さんのブログの標準MIDIファイル仕様(SMF)覚書にリンクがあります。

重要なリンクは、バックアップの為に当該ブログにも貼っておきます。
 
◆こちらはMIDI Manufacturers Association(MMA)のサイトに有る仕様書(英文)です。
 SMF仕様書  
 SMF追加仕様書

◆こちらは「有志」の方のHPです。太郎さんのブログに記載されたうち、2つは既に焼失しています。
 The MIDI Specification
 Introduction to Computer Music  
 "MIDI File Format" 
 A crash course on the standard MIDI specification
 MIDI File Parsing 
 詳説MIDI規格

| | コメント (0) | トラックバック (0)

ヤマハの音声合成技術

今回は、ヤマハの音声合成技術の推移を追ってみました。

◆1997年6月25日 インプレスPCウオッチ
メロディと歌詞によりリアルタイム音声合成が可能
性別や年齢など、細かく音声を指定可能

ヤマハ、歌を唄える新音源を開発。新発売のMIDI音源用拡張ボードとして発売

 

これが最初の音声合成に係わる製品と思います。PLG100-SGが唄う「木曽節」のサンプル音声を聞いてみましたが、出来上がりは.....微妙....。自分が音楽家だったら、この音声合成ボードは使わないと思います。

◆2003年12月16日 インプレス ケータイウオッチ
ヤマハ、人の声を合成できる音源に対応した制作ツール
 

このとき、携帯向け音源LSI MA-5 の音声合成機能を用いたコンテンツ製作ツールがリリースされました。MA-5 では、Voice Synthesis function by HV (Humanoid Voice) がカタログに訴求されていました。YAMAHAのサイトへのリンクが全て切れているので、音質は不明です。

◆2004年2月10日 窓の杜
ヤマハ、「Becky!」専用の音声合成プラグイン「Becky! HV Plug-in」を公開
メールの開封時に任意の音声を携帯電話からしゃべらせることができる

 

一企業が「窓の杜」にフリーソフトを提供し、かつメールを読ませるという課題に挑戦しているのにはちょっと意外でした。目的はMA-5を搭載した携帯との連携動作です。

ヤマハはこの時点では音声合成機能を HV (Humanoid Voice) の名称で売り込もうとしていたようです。


◆2005年6月10日 ITMedia
ヤマハ、“脱着メロ”の音源チップ「MA-7」投入
128和音、3D対応など最新機能に対応しながら、ミュージックプレーヤー機能との組み合わせを考慮。Class-Dアンプを内蔵し、スピーカーの消費電力を削減できる。

そして、最新の音源LSI MA-7 がリリースされました。MA-7 の合成音声は しゃべる絵本 for MA-7 で聞くことができます。

◆2007年8月31日 PCウオッチ
「VOCALOID 2」を使ったバーチャル歌手「初音ミク」が発売
-声優を自在に歌わせるソフトウェア音源

そして、今年8月に初音ミクが発売されました。

余談ですが、SMAF GLOBAL に、ヤマハのマルチメディア・データ形式のSMAF仕様書が掲載されています。もしかすると、VOCALOID の .vsq ファイルは、SMAFのデータ形式が流用されているのではと考えています。データ形式の設計には多大な労力が掛かるため、既存のものを流用することが多いためです。

| | コメント (0) | トラックバック (1)

Live Searchで初音ミクを画像検索!

いや、MSNサーチのトップページ右上なんですけどね。

Msn_hatsune_miku
もうちょっと拡大してみましょう。これで読めるかな。
Msn_hatsune_miku_up_2
いや、笑いましたよ。MSNの中の人も洒落がわかっている。
これだけ迅速に対処できるということは、恐らくファンの人がいるんでしょう。
初音ミクというと、某TV局で妙な紹介をされたり、画像検索がGoogle八分に有ったりと色んなことがありましたが、MSはこれを逆手にとってMSNサーチの宣伝とはやりますね。(笑)

追記:Internet Explorer だと、最初に一瞬だけ表示されますが、FireFox ならばずっと表示されたままになります。

初音ミクのネタついでに、オリジナル曲「あなたの歌姫」の3Dプロモーション画像付きを貼っておきます。いや、こんな面白いものばかり見られるんで、最近はTVってあまり見てないんですよね。ニコニコ動画の職人の諸兄に感謝です。

 

| | コメント (0) | トラックバック (0)

VOCALOIDの価値

世界初ツンデレボイスナビゲーション機能付のワンセグTV「SEGNITY」、このツンデレボイスに釘宮理恵が声を充てているとの話があります。

この製品の検証ビデオが以下にアップされています、

確かに釘宮ボイスで間違いないようですし、あたかもTVが感情を持ったかのように振舞うのは面白く感じますが、固定メッセージなので、買った当初は面白いと思っても、しばらく経つと飽きるんじゃないかとも思います。







この「ツンデレナビゲーションシステム」は特許出願中だそうですが、まだ未公開なのか公開公報を見ることはできませんでした。

いろいろな装置を作っていると、装置に喋らせたい場合は結構あります。例えば何らかの致命的なエラーが発生したときなどです。このときに音声でその旨が通知できたならば、よりユーザ・フレンドリーなインターフェースとなるのではないかと思います。

むかし、そういうメッセージを音声で出すときには、メロディICで「葬送行進曲」を流すのが定番だったのですけどね。葬送行進曲だけでは状況の詳しい説明ができないですから、合成音声で通知ができればと思っていました。
その音声も、いわゆる「機械音声」っぽいのだとユーザーに無茶苦茶嫌がられれるのですよね。「機械に使われているようで厭だ」とか「感覚的に耳から拒絶する」とかいう意見を聞きました。でも、VOCALOID は違います。知らずに聞いている人には、普通の人間の音声に聞こえ、拒否感は殆ど無いのではないかと思います。

現在の装置は、固定音声を予め録音することによって自然な人間の音声の通知を実現しています。しかし音声データをROMに焼きこんでいるため、SEGNITY のように予め想定したパターンの音声を通知することしかできませんし、そのパターンが膨大に多い場合には実装が極めて困難になります。

よって、状況に対応したメッセージを音声通知するツールとして、「VOCALOID」が活用できればと思うのです。もし VOCALOID がASIC化されて機器に組み込まれ、入力されたメッセージ文字列からリアルタイムに音声出力できるようになれば、装置のあらゆる使用状況において適切な音声通知ができると思います。具体的には、機器のエラーメッセージやガイダンスを音声で通知するなどです。他には、PCアプリケーションの製作者が、エラーメッセージやガイダンスを初音ミクに喋らせることも考えられます。

また、他のブログで、歌詞とメロディをサーバーに入力すると サーバーからMP3 の歌声データが出力されるという "VOCALOID-WEB-API" の概念が記載されていました。このような API が実装されたならば、WEB表現が更に多様化することになるのではないかとおもいます。具体的には、WEBページを音声で読み上げることが極めて簡単にできるようになりますので、自動車の運転中や、通勤電車の中などのように音声のみで情報収集しなければならない場面で、新聞や雑誌のWEBを音声で通知することにより時間が有効に活用できると思います。

| | コメント (3) | トラックバック (0)

DTMマガジン11月号

DTMマガジン11月号がすごいことになっていますね。いま現在のマーケットプレイスのロープライスが\4,545ですね。これって、定価\1,500の雑誌なのですけど、3倍のプレミア付きで中古が販売されています。

「この商品を買った人はこんな商品も買っています」の欄を見ると、初音ミクの需要者層がよくわかります。初音ミクは当然としても、アイドルマスターとPerfume・・・(笑)、Perfume だったら自分もちょっと欲しいので、口述試験が終わってからレコード店に行くかな。

| | コメント (0) | トラックバック (0)

初音ミクは連結式音声合成?!

これが、今年8月にベルギー・アントワープで開催された Interspeech2007 で発表されたVOCALOIDに関する最新の論文です。

Hideki Kenmochi, Hayato Ohshita [Center for Advanced Sound Technologies, Yamaha Corporation, Japan],
"VOCALOID – Commercial singing synthesizer based on sample concatenation"


斜め読みしてみましたが、VOCALOIDはフォルマント音声合成ではなく、連結式音声合成ですね。2002年当時の公開特許公報でフォルマントの語が頻出だったので、てっきりフォルマント音声合成だとばかり思い込んでおりました。

The Synthesis Engine receives score information, selects necessary samples from Singer Library and concatenates them. (4, Synthesis Engine)

シンセシス・エンジンはスコア情報を受領し、歌手ライブラリから必要とするサンプル音声を取得し、それらを結合する。(第4章、シンセシス・エンジンより、参考訳)

以下に、システムの概念図を引用します。歌詞(Lyrics)と音色(Note)を入力し、歌手ライブラリを元に歌声(Synthesis Output) を出力するというものです。

Vocaloid_kenmochi_ohshita

| | コメント (0) | トラックバック (0)

VOCALOID CVシリーズ02

ここのブログ に、VOCALOID CVシリーズ02に関する予測が記載されており、リンクを辿ると声優の下田麻美さんのブログに辿り付きます。

クリプトン(株)の「まぜてよ☆生ボイス」のミニちらしの写真や、「とある音声収録」などという意味深な記載がありますね。これは、下田麻美さんがCVシリーズ02という事なのでしょうか。

| | コメント (0) | トラックバック (0)

VOCALOID関連論文#2

Unisong: A Choir Singing Synthesizer
2006年10月に発表された論文で、著者は劔持秀紀さん、ジョルディボナダさん、Blaauw, Merlijnさん、Loscos, Alexさんの4名です
論文概要をざっと翻訳したものを以下記載します。多少怪しい翻訳ですがご容赦ください。

 コンピュータは合唱するように歌声を発生することを以下2つの方法で達成することができます: ただ一つの声のクローンによる変化か、又は本当のコーラス録音の連結です。現在において、これらの2つの方法の統合品質はそれぞれ自然さと明瞭さに欠けています。
 ユニソングは、スコアと歌詞によって高品質の合成音声の性能を得られるユーザ指定のコーラス歌声シンセサイザです。 この記事は、仮想の統合世代の途中に行われるコーラス録音スクリプトの人間の監督された自動分割、サンプルデータベースの創造、サンプル取得、変化、および連結を実現する全ての動作とテクニックについて説明します。シンセサイザは歌のサンプルでデモンストレーションをするでしょう。

VOCALOIDの次に劔持秀紀さん、ジョルディボナダさんが論文発表したのはコーラス音を自然に合成するという UNISONG です。UNISONG はどこまで製品開発が進んでいるのか楽しみであります。

次は説明ppt ファイルで、VOCALOID という題で、劔持秀紀さんと大下隼人さんの共著です。10月11日の情報処理学会の発表は、このパワーポイントファイルがベースとなるのではないかと推測しています。
このスライド17頁目に Miku (初音ミク)がいます。
このパワーポイント・ファイルは極めて判り易く、VOCALOIDファン必見です。
Yamaha_ppt

| | コメント (0) | トラックバック (0)

VOCALOID@DCAjニュース

2003年6月度DCAjセミナー「最先端「音楽ツール」の紹介」で、剣持秀紀氏がVOCALOIDの紹介セミナーの講師を努めておられます。やはり剣持氏は VOCALOID 開発リーダーなのでしょうね。

このときの様子は、DCAjニュースの26ページに掲載されており、要点を一部引用します。

『VOCALOID』は、OS「Windows 2000」および「同XP」上で動作する(CPU: Pentium III、1GHz以上、RAM:512MB以上を推奨)。MacOSについても対応を予定している。

という訳で、ヤマハにユーザーからの熱い要望が届けば、MacOS や Windows2000 での VOCALOID も実現されるかもしれません。(笑)

2006年3月には、デンソー・ブリヂストン・ヤマハ現場が欲しがる人材/Tech総研 で、剣持氏が VOCALOID開発者としてインタビューを受けています。このインタビューによると意外と現在の開発者は少ないのですね。2002年の VOCALOID 開発時に限定してエンジニアを集結したのでしょうか。

現在のこの開発メンバーは2人で行っています。海外の共同研究機関や、ソフトウェアのチェックする人などの関係者を含めても7~8人くらいですね。

情報処理学会 によると、来週の10月11日午後に、ヤマハ本社来客会館にて、剣持氏による VOCALOID の発表があるそうです。「今をときめく VOCALOID」ということで、普段を見られない一般の取材の方が詰め掛けそうですね。

| | コメント (0) | トラックバック (0)

VOCALOID関連論文

ジョルディボナダさんが執筆されたVOCALOID関連論文を発見しましたので、特に重要とおもわれる初期の論文を2編ほどご紹介します。

Bonada, J. Loscos, A. Cano, P. Serra, X. 2001.
'Spectral Approach to the Modeling of the Singing Voice'
(歌声のモデルへの周波数からの観点)
Proceedings of 111th AES Convention; New York, USA

これが最も基礎となるVOCALOID関連論文です。
共同執筆者 Serra,X は、VOCALOID 関連特許を多く発明されているザビエルセラさんと思われます。
ヤマハアドバンストシステム開発センターの劔持秀紀さんが共著者として記載されています。

図10にシステム概念図が示されています。歌詞(Lyrics)と音階(Melody)と表現(Expression) を入力し、歌手データベースを元にして歌手シンセサイザが歌声を合成するというもので、VOCALOIDの概念が明確に記載されています。

Jordibonata_2001

 

Bonada, J. Celma, O. Loscos, A. Ortolà, J. Serra, X. 2001.
'Singing Voice Synthesis Combining Excitation plus Resonance and Sinusoidal plus Residual Models'
(歌声に統合する励振共鳴と正弦波様、及び残差モデリング)
Proceedings of International Computer Music Conference 2001; Havana, Cuba

ヤマハアドバンストシステム開発センターの劔持秀紀さん、久湊裕司さん、吉岡靖男さん、Hiraku Kayamaさんが共著者として記載されています。

システム構成図は基本的に VOCALOID2 初音ミクと同一です。

Jordibonata_2001a

| | コメント (0) | トラックバック (0)

「ヤマハの技術は世界一よ~♪」#2

フォルマント音声合成の米国登録特許について調べて見ました。
まずは、出願人毎のグラフを以下に示します。ヤマハの登録特許が群を抜いて多いことがわかります。
Formant_usp
ヤマハは、日本及び米国でフォルマント音声合成に関する最多の特許ポートフォリオを有しており、「ヤマハの技術は世界一」であることが数字で裏付けられました。

ところで、果たしてヤマハ(株)自身は、VOCALOID の価値について本当に気づいているんでしょうかね? VOCALOID 開発により少なくとも数千億円規模の市場を掘り当てたと思うのですが、その価値をきちんと把握して的確なマーケッティングを行ったのが、開発元のヤマハ(株)ではなく、販売先であるクリプトン(株)だったというのが何とも皮肉なものです。

VOCALOID の価値は「汎用テキストを感情を込めた音声に自動変換できる」点にあります。単に音楽関係のツールという位置付けは、VOCALOID の価値を矮小化するものでしょう。

おまけに、初音ミクのオリジナル曲として最も有名と思われる「みくみくにしてあげる♪」及び「あなたの歌姫」を貼っておきます。既に自分のiPod のプレイリストに「初音ミク」を作成し、この曲を転送済みです。

| | コメント (0) | トラックバック (0)

「ヤマハの技術は世界一よ~♪」

初音ミクのキャラクターソングとして有名な「おしえて! だぁりん 」の歌詞をふと思い出し、同一技術に措ける他社特許との比較をおこなってみました。

公開特許公報 特開平10-49192「歌唱音合成装置」  などによると、初音ミクに用いられている技術は、「フォルマント合成」というものです。詳しくはフォルマントシンギング音源講座 」をご覧ください。

Wikipedia のフォルマント には以下記載されています。

言葉を発している人の音声スペクトルを観察すると、複数のピークが時間的に移動していることが分かる。このピークをフォルマント、またはホルマントと言う(英語表記はformant)。 周波数の低い順に第一フォルマント第二フォルマント…という様に数字を当てて呼び、それぞれF1, F2とも表記する(第0フォルマント、F0を数える場合もある)。フォルマントの周波数は声道の形状と関係し,個体差や性差もフォルマントの違いを生む原因となる。 発音する音韻が同じであれば、各フォルマント周波数は近い値になる。

よって、フォルマント合成に係る特許出願の国内特許出願人を調べると、「ヤマハの技術は世界一よ~♪」の検証がおこなえることになります。(笑)
調査したところ、出願人別の出願数でいうと、ヤマハと松下電器産業が同数1位で61件、3位が東芝、4位がソニー、5位がNTTでした。
前記5社の出願年度毎の特許出願件数は以下のものです。
Formant_onsei_gousei
最近5年の出願数でいうと、ヤマハ(株)の出願数が群を抜いて多いことがわかります。よって、ヤマハ(株)は、フォルマント音声合成に関して日本一の特許ポートフォリオを有するということが裏付けられました。(笑)

松下電器産業(株)を出願人とする最近の公開特許公報から、聴覚障害者の発音を聞きやい声にリアルタイム変換する事を技術課題としていることが判りました。しかし、最近の出願数は極めて少なく、フォルマント音声合成の技術開発は止めてしまったようです。

うちの奥さんはフォルマント音声合成について、「振り込め詐欺に使われたら困るわね。」と言っていました。そういう切り口で見たことはなかったので、意外な視点でした。

| | コメント (0) | トラックバック (0)

初音ミク関連情報

初音ミクは情報を入手すればするほど、「これは使える!」と、心がうずく製品です。口述試験が終わったら早速入手して使用してみたいものです。自分自身は、「初音ミクが読み上げる工業所有権法(特実意商)」で勉強することは出来なさそうですが、来年度の受験生達に間に合わせられるかな?

以下に、初音ミク関連情報リンクを貼っておきます。

「VOCALOID 2」を使ったバーチャル歌手「初音ミク」が発売

クリプトン・フューチャー・メディア株式会社は、人間の声をもとにした音声合成エンジン「VOCALOID 2」を採用したソフトウェア音源として、バーチャルアイドル歌手「初音ミク」を8月31日に発売する。価格はオープンプライス。直販サイトでは 16,275円で販売されている。対応OSはWindows XP/Vista。

初音ミク - Wikipedia

初音ミク(はつね みく)は2007年8月31日クリプトン・フューチャー・メディアから発売されたデスクトップミュージックを制作する音声合成ソフトである。また、このソフトを用いて作られた楽曲のボーカルの名称を指して呼ぶこともある。

VOCALOID 2 キャラクター・ボーカル・シリーズ(CVシリーズ)の第1弾となるライブラリである。ちなみに第2弾を2007年12月に、第3弾を2008年にそれぞれ発売予定。


声優NEWS.COM/話題沸騰の「VOCALOID2 初音ミク」の開発元クリプトンに質問してみた

各所で話題沸騰の「初音ミク HATSUNE MIKU 」はクリプトン・フューチャー・メディア株式会社が開発したメロディと歌詞を入力するとその通り歌う音声合成ソフト。声を担当した藤田咲さんのキュートで 透明感のある歌声と、機械とは思えない自然な発声が人気となっている。
そんな夢のソフトウェア「初音ミク」の気になるところを開発元であるクリプトン・フューチャー・メディア株式会社様に聞いてみた。
(以下はリンクにて)

ニコニコ動画で歌う「初音ミク」って誰? 産経新聞

 コメントをつけて楽しむ動画投稿サイト「ニコニコ動画(RC)」で、「初音ミクに○○を歌わせてみた」といった投稿が急増、人気ランキング上位にも連日 登場している。動画を再生すると聞こえてくるのはアニメのような少女の歌声だが、実はこの歌声、8月31日に発売された音楽制作ソフト「初音ミク」で作り 出した合成音声だ。(以下はリンクにて)

VOCALOID @wiki

VOCALOID 紹介サイト

| | コメント (0) | トラックバック (0)

VOCALOIDの基礎出願

先日のブログで、VOCALOIDの基礎出願を紹介しましたが、こちらの方が出願日が先であり、基礎出願としてはこちらが相応しいと判断します。

特開平9-50287 「自動歌唱装置」

【課題】 自動歌唱装置において、より自然な歌声を発生させる。
【解決手段】 文字テキスト入力操作部6から歌詞データをテキストデータの形式で入力し、歌詞シーケンスデータに変換して、データメモリ4に格納する。データメモリ4には、音符に対応するメロディシーケンスデータも格納され、該メロディシーケンスデータの読み出しに応じて、前記歌詞シーケンスデータも読み出される。このとき、歌詞シーケンスデータ中に単一の音符に対して同時に発音すべき音節であることを示すフラグが記載されていると、同一のメロディシーケンスデータに対して複数の歌詞シーケンスデータが読み出され、各歌詞シーケンスデータに基づいて、音源部10の無声音成分発音グループ12に属する音源および有声音成分発音グループ11に属する音源から、それぞれ、子音と母音とが発音され、これらが合成されて音声出力される。

| | コメント (0) | トラックバック (0)

ポンペウファブラ大学

日光を放つブロックを透明な円形のテーブルの上で動かすと音を奏でられるという、新しい楽器『reactable』。

http://creditnews.blog101.fc2.com/blog-entry-1291.html
これが、VOCALOID「初音ミク」の主要な発明者のひとりであるジョルディボナタさんの出身であらせられるポンペウファブラ大学の音楽技術研究者たちによる博士号プロジェクトとして開発されたものです。この大学は、音楽関連に造詣が深いのでしょうか。

ついでに、和めるキャラソンを貼っておきます。なんとオリジナルソングです。こういう使い方がVOCALOIDの本来の使い方なのだと思います。

| | コメント (0) | トラックバック (0)

初音ミクの特許出願について

「初音ミク」に用いられている音声合成技術は、ヤマハが開発したものです。よって、ヤマハの音声合成に係る特許出願を調査することで、開発の推移を調べてみました。

以下に、ヤマハが出願人となっている特許のうち、音声合成に係る特許の出願数の推移のグラフを表示します。

 Yamaha

1998年以前は、音声合成とはいっても、カラオケで歌う歌声を加工して、あたかも原歌手が歌っているかのようにリアルタイムに音声加工する発明ばかりです。

特開平5-204397「音声分析合成装置」

特開平8-194495「カラオケ装置」

1998年に、特開平10-49192「歌唱音合成装置」 が出願されます。この時点でヤマハのエンジニアは、予め取り込んだ歌声から新たな歌唱を再構成することに価値が有ることに気付いたようです。すなわち、これがVOCALOIDの基礎出願と思われます。

【課題】 歌詞データに対応して高品質の歌唱音を合成する。
【解決手段】 音源部20には有声音フォルマント成分を生成する有声音成分音源(VTG)グループ21と無声音フォルマント成分を生成する無声音成分音源(UTG)グループ22とからなるフォルマント合成音源と、無声子音の音声波形が格納された波形メモリを有するPCM音源23とが設けられている。ROM11には制御プログラムのほかに、各音韻を発声するための音韻パラメータと、先行音韻と後続音韻とのわたりの部分の制御パラメータである調音結合パラメータとが記憶された音韻データベースが格納されている。データメモリ13中には楽曲の歌詞データと伴奏データなどからなるソングデータが格納されており、この歌詞データに基づいて前記音韻データベースから対応するパラメータを読み出し前記音源部20により対応する音声を合成出力する。このとき、無声子音は前記PCM音源23により発声させる。

その後の改良発明に係る出願を以下に列挙します。主に2002年度以降に出願されています。

特開平11-15489「歌唱音合成装置」

特開2002-221978「ボーカルデータ生成装置、ボーカルデータ生成方法および歌唱音合成装置」

この出願では、既に「バーチャルシンガ」という概念が記載されています。

【課題】 音節を構成する音素のうち、子音に対向する音素を音符の発生タイミングにあわせて発声することにより、伴奏に合わせたバーチャルシンガによる自然な歌唱を実現する。

特開2002-268658「音声分析及び合成装置、方法、プログラム」

特開2003-255974「歌唱合成装置、歌唱合成方法及び歌唱合成用プログラム」

特開2003-255998「歌唱合成方法と装置及び記録媒体」

特開2004-4440「歌唱合成装置、歌唱合成用プログラム及び歌唱合成用プログラムを記録したコンピュータで読み取り可能な記憶媒体」

特開2004-061753「歌唱音声を合成する方法および装置」

特開2004-061793「歌唱合成装置、歌唱合成方法並びに歌唱合成用プログラム」

特開2004-077608「合唱合成装置、合唱合成方法およびプログラム」

発明者は、ジョルディボナタ、劔持秀紀、久湊裕司の3名が目立ちます。開発チームは2002年に組織され、恐らく10名~15名で構成されていると思われます。

出願人は、ヤマハ株式会社のほか、ポンペウファブラ大学が名前を連ねています。この大学はバルセロナにある大学で、かなり先進的な研究をおこなっています。

2003年2月に、歌詞とメロディを入力すると歌い出す ヤマハが歌声合成ソフト開発 の発表がなされます。

最近の公開特許公報から推測すると、VOCALOIDのアプリケーションの本命は、携帯電話に実装してメールを読み上げることのようです。いまだにそのアプリケーションは世に出ておりませんが、ヤマハ(株)がうまくこの事業を成功することを祈っております。

特開2006-119655「音声合成装置」

ヤマハ株式会社に置かれましては、釘宮理恵のVOCALOIDを携帯電話に組み込んで商品化いただくように、よろしくお願いいたします。(お約束)

| | コメント (0) | トラックバック (0)

初音ミクの商標登録出願

「初音ミク」で商標登録出願及び登録商標を検索しましたがヒットしませんでした。クリプトンフューチャーメディアさんには、是非とも商標登録出願いただくことをお勧めいたします。
出願なき場合には、パクリ商品やら関連商品が山のように出され、初音ミクのブランドイメージが毀損される蓋然性が高くなります。
DTMマガジンの試用版で、更にブームに火がつくのではないかと思いますので、出願は急がれた方がよいと思います。
次の商品は、『歌わなくていいから、単に抑揚をつけてテキストを読むだけ」機能の追加も宜しくお願い致します。iPod に転送して聞けばそれでいいのです。
「特許法 1条から204条まで、by 初音ミク」な~んて商品があったら是非とも書いたいものです。
次回は、初音ミク関連の特許出願の話で、YAMAHA及びスペインの大学の研究者の協業だということが判明しました。その話について詳しく追ってみたいと思います。

| | コメント (0) | トラックバック (0)

VOCALOIDの商標登録

初音ミク関連商品の商標登録又は商標登録出願を調べてみました。さすが、先代VOCALOID の MEIKO の発売時にちゃんと出願していますね。2つに分けて出願している理由は謎です。
VOCALOIDの正式称呼はボカロイド又はボキャロイドだったのですね。ボーカロイドと長音になるものだとばかり思っていました。

【商標登録番号】    第4813643号
【登録日】    平成16年(2004)10月29日
【登録公報発行日】    平成16年(2004)11月30日
【公開日】    平成16年(2004)4月8日
【出願番号】    商標出願2004-24163
【出願日】    平成16年(2004)3月15日
【先願権発生日】    平成16年(2004)3月15日
【存続期間満了日】    平成26年(2014)10月29日
【商標(検索用)】    VOCALOID
【標準文字商標】    VOCALOID
【称呼】    ボカロイド
【権利者】   
【氏名又は名称】    ヤマハ株式会社
【住所又は居所】    静岡県浜松市中区中沢町10番1号
【区分数】    2
【商品及び役務の区分並びに指定商品又は指定役務】
    38    電気通信(放送を除く。),放送,報道をする者に対するニュースの供給,電話機・ファクシミリその他の通信機器の貸与,メッセージの送信のための通信,電子メールによる通信,コンピュータを利用したメッセージ及び映像による通信,電子掲示板による通信
    42    気象情報の提供,建築物の設計,測量,地質の調査,機械・装置若しくは器具(これらの部品を含む。)又はこれらの機械等により構成される設備の設計,デザインの考案,電子計算機のプログラムの設計・作成又は保守,電子計算機・自動車その他その用途に応じて的確な操作をするためには高度の専門的な知識・技術又は経験を必要とする機械の性能・操作方法等に関する紹介及び説明,医薬品・化粧品又は食品の試験・検査又は研究,建築又は都市計画に関する研究,公害の防止に関する試験又は研究,電気に関する試験又は研究,土木に関する試験又は研究,農業・畜産又は水産に関する試験・検査又は研究,機械器具に関する試験又は研究,著作権の利用に関する契約の代理又は媒介,社会保険に関する手続の代理,計測器の貸与,電子計算機の貸与,電子計算機用プログラムの提供,理化学機械器具の貸与,製図用具の貸与

【商標登録番号】    第4722616号
【登録日】    平成15年(2003)10月31日
【登録公報発行日】    平成15年(2003)12月2日
【公開日】    平成15年(2003)3月20日
【出願番号】    商標出願2003-12777
【出願日】    平成15年(2003)2月19日
【先願権発生日】    平成15年(2003)2月19日
【更新登録日】   
【存続期間満了日】    平成25年(2013)10月31日
【商標(検索用)】    VOCALOID
【標準文字商標】    VOCALOID
【称呼】    ボカロイド,ボキャロイド
【権利者】   
【氏名又は名称】    ヤマハ株式会社
【住所又は居所】    静岡県浜松市中区中沢町10番1号
【付加情報】    標準文字
【国際分類版表示】    第8版
【区分数】    3
【商品及び役務の区分並びに指定商品又は指定役務】
    9    耳栓,加工ガラス(建築用のものを除く。),アーク溶接機,金属溶断機,電気溶接装置,オゾン発生器,電解槽,検卵器,金銭登録機,硬貨の計数用又は選別用の機械,作業記録機,写真複写機,手動計算機,製図用又は図案用の機械器具,タイムスタンプ,タイムレコーダー,パンチカードシステム機械,票数計算機,ビリングマシン,郵便切手のはり付けチェック装置,自動販売機,ガソリンステーション用装置,駐車場用硬貨作動式ゲート,救命用具,消火器,消火栓,消火ホース用ノズル,スプリンクラー消火装置,火災報知機,ガス漏れ警報器,盗難警報器,保安用ヘルメット,鉄道用信号機,乗物の故障の警告用の三角標識,発光式又は機械式の道路標識,潜水用機械器具,業務用テレビゲーム機,電動式扉自動開閉装置,乗物運転技能訓練用シミュレーター,運動技能訓練用シミュレーター,理化学機械器具,写真機械器具,映画機械器具,光学機械器具,測定機械器具,配電用又は制御用の機械器具,回転変流機,調相機,電池,電気磁気測定器,電線及びケーブル,電気アイロン,電気式ヘアカーラー,電気ブザー,電気通信機械器具,電子応用機械器具及びその部品,磁心,抵抗線,電極,消防艇,ロケット,事故防護用手袋,防じんマスク,防毒マスク,溶接マスク,防火被服,眼鏡,家庭用テレビゲームおもちゃ,携帯用液晶画面ゲームおもちゃ用のプログラムを記憶させた電子回路及びCD-ROM,スロットマシン,ウエイトベルト,ウエットスーツ,浮袋,運動用保護ヘルメット,エアタンク,水泳用浮き板,レギュレーター,レコード,メトロノーム,電子楽器用自動演奏プログラムを記憶させた電子回路及びCD-ROM,計算尺,映写フィルム,スライドフィルム,スライドフィルム用マウント,録画済みビデオディスク及びビデオテープ,電子出版物,ダウンロード可能な音楽又は音声,ダウンロード可能な画像(動画を含む),ダウンロード可能なカラオケ用の画像・楽曲・歌詞,ダウンロード可能な電子楽器用自動演奏プログラム,電子計算機端末による通信で提供される電子計算機用プログラム又は家庭用テレビゲームソフト
    15    調律機,電気又は電子楽器用アンプ,その他の楽器,電気又は電子楽器用エフェクター,その他の演奏補助品,音さ,電子楽器制御用データにより楽音を発生させる音源装置,ミュージックシーケンサー,楽音サンプラー(電子楽器用のものに限る。),自動リズム演奏装置
    41    当せん金付証票の発売,技芸・スポーツ又は知識の教授,献体に関する情報の提供,献体の手配,セミナーの企画・運営又は開催,動物の調教,植物の供覧,動物の供覧,電子出版物の提供,図書及び記録の供覧,美術品の展示,庭園の供覧,洞窟の供覧,書籍の制作,映画・演芸・演劇又は音楽の演奏の興行の企画又は運営,映画の上映・制作又は配給,演芸の上演,演劇の演出又は上演,音楽の演奏,放送番組の制作,教育・文化・娯楽・スポーツ用ビデオの制作(映画・放送番組・広告用のものを除く。),放送番組の制作における演出,映像機器・音声機器等の機器であって放送番組の制作のために使用されるものの操作,ゴルフの興行の企画・運営又は開催,相撲の興行の企画・運営又は開催,ボクシングの興行の企画・運営又は開催,野球の興行の企画・運営又は開催,サッカーの興行の企画・運営又は開催,興行の企画・運営又は開催(映画・演芸・演劇・音楽の演奏の興行及びスポーツ・競馬・競輪・競艇・小型自動車競走の興行に関するものを除く。),競馬の企画・運営又は開催,競輪の企画・運営又は開催,競艇の企画・運営又は開催,小型自動車競走の企画・運営又は開催,音響用又は映像用のスタジオの提供,運動施設の提供,娯楽施設の提供,映画・演芸・演劇・音楽又は教育研修のための施設の提供,興行場の座席の手配,映画機械器具の貸与,映写フィルムの貸与,楽器の貸与,運動用具の貸与,テレビジョン受信機の貸与,ラジオ受信機の貸与,図書の貸与,レコード又は録音済み磁気テープの貸与,録画済み磁気テープの貸与,ネガフィルムの貸与,ポジフィルムの貸与,おもちゃの貸与,遊園地用機械器具の貸与,遊戯用器具の貸与,書画の貸与,写真の撮影,通訳,翻訳,カメラの貸与,光学機械器具の貸与,映画の上映・演芸の上演・演劇の演出又は上演・音楽の演奏に関する情報の提供,映画・演芸・演劇又は音楽の演奏の興行の企画又は運営に関する情報の提供,音楽に関するコンテスト又はオーディションの企画・運営又は開催,セミナー・研究会・研修会・講演会・シンポジウムの企画・運営又は開催,委託による音楽の作詞・作曲・編曲,音楽ビデオの制作,通信を用いて行う音楽又は音声の提供,通信を用いて行う画像の提供(動画を含む),通信を用いて行うゲームの提供,通信を用いて行うカラオケのための画像・楽曲・歌詞の提供

| | コメント (0) | トラックバック (0)

Vocaloid2 初音ミク

合成音声でいろいろ調べると、こんなものを見つけてしまいました。


VOCALOID2 初音ミクという商品で、歌詞と旋律を入力すると、その曲を萌えボイスで歌ってくれ、音楽プロデューサ気分が味わえるというものです。

詳しい記事は以下にあります。
萌えボイスで自作曲を歌ってくれる「初音ミク」 ITMedia News より

異例の売れ行き「初音ミク」 「ニコ動」で広がる音楽作りのすそ野 ITMedia Newsより

こちらは製作元の記事です。
クリプトン VOCALOID2特集

元々は、ヤマハが開発した音声合成ソフトウエアのライセンス供与を受けたもののようです。2003年当時でも、既に現在の「初音ミク」とほぼ同じインターフェースを持っています。
歌詞とメロディを入力すると歌い出す ヤマハが歌声合成ソフト開発


どんなことが出来るかは、YouTube にアップロードされた作品をご覧いただければと思います。

初音ミクが歌うヨドバシカメラの歌 x516

初音ミクが歌う「そらのむこう」 x1,933

初音ミクに冒険でしょでしょ?を歌わせてみた Ver1.3 x6,262 

初音ミクに「風になる」を歌って貰った(修正版) x1,771

【ミクカバー】初音ミクでBeautiful World/宇多田ヒカルを歌ってみた x9,441

ニコニコ動画には、更に多数の作品がアップロードされていますので、「初音ミク」のキーワードで検索願います。
既に、「青本や条文を読ませる」なんてレベルではなく、きちんと抑揚と感情を込めています。ちと手間は掛かるかもしれないですが、実際にバーチャル講義をさせることができるレベルと思います。
クリプトンの企画部の方には、是非ともVOCALOID2 釘宮理恵バージョンを作成いただきたく、よろしくお願いします。

| | コメント (1) | トラックバック (0)