5
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

Livebook で VOICEVOX の「ずんだもん」や「WhiteCUL」に喋ってもらう

Last updated at Posted at 2023-07-26

はじめに

@t-yamanashi さんの記事を参考に、 Livebook で VOICEVOX の ずんだもん や WhiteCUL に喋ってもらいました

実装したノートブックはこちら

クレジット

VOICEVOX:ずんだもん

VOICEVOX:WhiteCUL

VOICEVOX とは

商用・非商用問わず無料で使えるテキスト読み上げソフトウェアです

様々なキャラクターの音声でテキストを読み上げることができます

音声の利用については各音声の利用規約に則ります

実行環境

  • macOS Ventura 13.4.1
  • VOICEVOX 0.14.7
  • Elixir 1.15.4
  • Erlang 26.0.2
  • Livebook 0.10.0

事前準備

VOICEVOX 公式から VOICEVOX をインストールし、起動しておきます

VOICEVOX を起動している状態では、 http://localhost:50021 で VOICEVOX の API が呼び出せます

また、以下の URL で API の仕様を確認できます

http://localhost:50021/docs

やはり OpenAPI は偉大

これさえ参照すれば Elixir から VOICEVOX を操作し放題です

スクリーンショット 2023-07-26 16.12.33.png

この状態で Livebook を起動し、ノートブックを作成します

セットアップ

Mix.install([
  {:kino, "~> 0.10"},
  {:req, "~> 0.3"}
])

音声出力等のために Kino 、 VOICEVOX API へのリクエストのために Req をインストールしています

音声一覧の取得

VOICEVOX には 2023年7月現在、 26 キャラクターの音声が存在します

また、各キャラに「ノーマル」「たのしい」「かなしい」「びえーん」などのスタイルが複数存在します

音声を喋ってもらうとき、どの声にするのかを指定する必要があるため、まずは音声ID、キャラクター、スタイルの一覧を取得し、目当ての音声を探します

音声一覧を取得するためには core_version を指定する必要があります

以下のコードを実行し、 VOICEVOX の core_version を取得します

core_version =
  "http://localhost:50021/core_versions"
  |> Req.get!()
  |> Map.get(:body)
  |> Enum.at(0)

実行結果は "0.14.4" になります

VOICEVOX 本体のバージョンは 0.14.7 ですが、コアのバージョンは 0.14.4 のようです

では、この値を使って音声の一覧を取得します

Req.new(url: "http://localhost:50021/speakers", params: %{core_version: core_version})
|> Req.get!()
|> Map.get(:body)
|> Enum.flat_map(fn speaker ->
  speaker["styles"]
  |> Enum.map(fn style ->
    %{
      name: speaker["name"],
      id: style["id"],
      style_name: style["name"]
    }
  end)
end)
|> Enum.sort_by(& &1.id)
|> Kino.DataTable.new()

スクリーンショット 2023-07-26 17.15.59.png

id: 0 が「四国めたん」の「あまあま」、 id: 1 が「ずんだもん」の「あまあま」というように一覧が取得できました

この一覧から id を選択し、音声を喋ってもらいます

音声合成

まず「ずんだもん」の「ノーマル」に喋ってもらいます

喋ってもらいたい内容を text に指定し、「ずんだもん」「ノーマル」の音声id 3 を指定します

先に音声合成用のクエリを生成します

クエリ生成によってテキストをカナに変換し、各音毎に高さやアクセントを設定しています

その後、生成したクエリを使って音声合成し、結果として音声のバイナリデータを取得します

text = "ずんだもんなのだ。エリクサー使いのアルケミストになったのだ"
speaker_id = 3

# 音声合成用のクエリを生成する
audio_query =
  Req.new(
    url: "http://localhost:50021/audio_query",
    params: %{
      text: text,
      speaker: speaker_id
    }
  )
  |> Req.post!()
  |> Map.get(:body)

# クエリを使って音声を合成する
data =
  Req.new(
    url: "http://localhost:50021/synthesis",
    params: %{speaker: speaker_id}
  )
  |> Req.post!(json: audio_query)
  |> Map.get(:body)

音声再生

VOICEVOX から取得したバイナリのままでは Web 上で再生できないので、 Base64 エンコードします

base64 = Base.encode64(data)

結果は "UklGRiRSBABXQVZFZm10IBAAAAABA..." というような長い文字列になります

この文字列を HTML の audio タグの src に指定することで音声を再生します

Kino.HTML.new("""
<audio controls src="data:audio/wav;base64,#{base64}">
</audio>
""")

モジュール化

使いやすいようにモジュール化しました

defmodule VoiceVox do
  @base_url "http://localhost:50021"

  defp get_audio_query(text, speaker_id) do
    Req.new(
      url: "#{@base_url}/audio_query",
      params: %{
        text: text,
        speaker: speaker_id
      }
    )
    |> Req.post!()
    |> Map.get(:body)
  end

  defp synthesis(audio_query, speaker_id) do
    Req.new(
      url: "#{@base_url}/synthesis",
      params: %{speaker: speaker_id}
    )
    |> Req.post!(json: audio_query)
    |> Map.get(:body)
  end

  defp view(data) do
    base64 = Base.encode64(data)

    Kino.HTML.new("""
    <audio controls src="data:audio/wav;base64,#{base64}">
    </audio>
    """)
  end

  def new(text, speaker_id) do
    text
    |> get_audio_query(speaker_id)
    |> synthesis(speaker_id)
    |> view()
  end
end

今度はVOICEVOXの「面白い女」で有名な「WhiteCUL」「びえーん」で喋ってもらいます

VoiceVox.new("こんにちは。WhiteCULです。今日はライブブックから喋っています", 26)

まとめ

VOICEVOX は API を備えているので、 Elixir からも簡単に操作できました

また、音声データも Base64 エンコーディングすることで Livebook 上で再生できました

実は初めて YouTube に動画を投稿したので、これからちょくちょく Livebook ネタを投稿していこうと思います

5
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
5
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?