2015年6月12日金曜日

[Raspbery Pi]天気予報をしゃべる目覚まし時計

Raspberry Piで天気予報をしゃべる目覚まし時計を作ってみました。


天気予報はWeather Hacks様で調べることにしました。
音声ファイルはdocomo Developer support様の音声合成で作ります。
Open JTalkを使う方法もあるようです。詳しくは第20回「ラズベリーパイで手作り目覚まし時計!(2)音声アラーム編」。とても詳しく書かれています。

Rubyで作りました。
$ ruby -v
ruby 2.0.0p645 (2015-04-13 revision 50299) [armv7l-linux-eabihf]

ソースコードはこんな感じです。
docomo Developer supportの音声合成API Keyは取得したものを記載してください。

あとはこれを$ crontab -e とかで
45 6 * * * <command>
みたいなのを書いておけば6:45に天気予報をしゃべってくれます。
cronも第19回「ラズベリーパイで手作り目覚まし時計!ストップボタン編」の説明をご紹介しておきます。
参考にさせていただきました。ありがとうございます。


require 'open-uri'
require 'json'
require 'uri'

# http://weather.livedoor.com/weather_hacks/
class Weather
  attr_accessor :id

  BASE_URL = 'http://weather.livedoor.com/forecast/webservice/json/v1?city='

  def initialize(id)
    @id = id
  end

  def get
    json = nil
    open("#{BASE_URL}#{id}") do |f|
      json = f.inject('') do |memo, line|
        memo + line
      end
    end
    parse(json)
  end

  private
  def parse(json_text)
    json = JSON.parse(json_text)
    "今日の" + json['location']['prefecture'] + json['location']['city'] + "の天気は" + json['forecasts'][0]['telop'] + 'です'
  end
end

# https://dev.smt.docomo.ne.jp/
class TextToFile
  attr_accessor :msg, :speaker, :file_path

  # https://dev.smt.docomo.ne.jp/?p=docs.api.page&api_name=text_to_speech&p_name=api_hoya#tag01
  API_KEY = 'Your API Key'
  URL = "https://api.apigw.smt.docomo.ne.jp/voiceText/v1/textToSpeech?APIKEY=#{API_KEY}"

  def initialize(opts)
    @msg = opts[:msg]
    @speaker = opts[:speaker]
    @speaker ||= %w(show haruka hikari takeru santa bear).sample(1)[0]
    @file_path = opts[:file_path]
  end

  def to_file
    uri = URI.parse(URL)
    https = Net::HTTP.new(uri.host, uri.port)

    https.use_ssl = true
    req = Net::HTTP::Post.new(uri.request_uri)

    req["Content-Type"] = "application/x-www-form-urlencoded"
    req.body = "text=#{URI.encode(msg)}&speaker=#{speaker}&speed=50&format=wav"

    res = https.request(req)

    File.open(file_path, 'wb') do |file|
      file.write(res.body)
    end
  end
end

# 調べたい地域のIDを指定してください。
# http://weather.livedoor.com/forecast/rss/primary_area.xml
w = Weather.new('130010')
TextToFile.new(msg: w.get, speaker: 'haruka', file_path: 'speech.wav').to_file

`aplay speech.wav`




0 件のコメント:

コメントを投稿