2016年11月13日

Arduino based game console "Arduboy" first impression (August 17, 2016)

arduboy01.jpg

I got an "Arduboy" at the venue of Maker Fair Tokyo 2016.

This is a portable game machine combining Arduino Leonardo equivalent CPU and 180 mAh battery, SSD1306 OLED display, piezoelectric buzzer, operation buttons.
The selling price at the venue was 5,000 yen.
Even buying parts individually will not be so cheap.
Anyway I bought it because the making of the casing was very good.

Although the appearance is a game machine style, it is a wonderful Arduino compatible machine.
Since the USB connector is built in, all you need is just connecting the cable.
Of course, you can write programs in Arduino IDE and run it normally.


arduboy0.jpg


For the setup etc of the development environment, the following page is detailed.

【Kickstarter】Arduboyレビュー、インストール手順、面白いゲーム紹介など - t-miyajima blog

However, one thing that needs attention is "It will not work with Arduino 1.6.10."
During compilation I got an error saying
-fno-fat-lto-objects are supported only with linker plugin.
and it stops.
(8/19 update: Arduino 1.6.11 has been released, it works fine.)
This seems to be caused by inconsistency of Arduino IDE and Arduboy library.
Arduino 1.6.9 works without problems.

Cannot Compile or Upload an Example Game: cc1.exe: error [SOLVED] - Arduboy / Issues - Community


As the first step, I tested some games and samples attached to the Arduboy library.

*Hello, World!
A Sample displays characters on the OLED. The code is here .
arduboy02.jpg


*ArduBreakout
A breakout with button operation. The code is here.
arduboy03.jpg


*GLOVE
A " Gauntlet " style game. Well done.
The compiler reported "Sketch uses 28,612 bytes (99%) of program storage space. Maximum is 28,672 bytes. Global variables use 1,682 bytes (65%) of dynamic memory, leaving 878 bytes for local variables." which means that the author stuffed code and data in as much as he can.
arduboy04.jpg


*伊for Arduboy
A side scrolling shooter. I impressed that it can move objects much more than I had thought.
arduboy05.jpg


Looking at the community site , it seems that 27 games are currently registered in the wiki.
There were also various demos that were not games including a demonstration of RPG similar to the Legends of Zelda.

Arduventure
[WIP] Arduventure (RPG) - Arduboy / Development - Community

arduboy06.jpg


An introduction of various works is in the following article.

11 Arduboy Games worth Playing - Retro Gaming Magazine | Retro Gaming Magazine

Original post in Japanese: ゲーム機型Arduino「Arduboy」を動かしてみた: 楽しくやろう。
ラベル:english Arduboy
posted by boochow at 13:46| Comment(0) | Arduino | このブログの読者になる | 更新情報をチェックする

2016年11月06日

FM音源をArduboyで動かしてみた の続き


前回の続きです。
やはり16ステップのシーケンスが1つ使えるだけでは物足りないので、シーケンサー周りをグレードアップしました。
具体的には

・シーケンスは16個(個々のシーケンスは16ステップで変わらず)
・シーケンスの連続演奏
・シリアルポート経由でのシーケンスのインポート/エクスポート
・EEPROMへの保存

といった機能を実装しました。
そのほか、

・直前の音を消さない「タイ」と直前の音を消す「休符」を分けて実装
・1ステップを四分音符から八分音符へ変更

などの拡張も行っています。
以下のGitHubリポジトリも更新しました。(前回のものはリリースv1.0として保存してあります。)

boochow/abSynth-FM: FM Synthesizer with step sequencer for Arduboy

前回からコードを整理せずにそのまま拡張したので、相変わらず中身はきれいではありません。
行数は現時点でインベーダーゲームより多い1700行超になっていますが、ビットマップやプリセットで用意した曲データ、Protonで開発するためのシリアルポート入力の代替コードなどを含んでいます。

プログラミングとしては、シーケンスの選択や通信を行うユーザーインタフェースと、シリアルポートからの入力のパーサが主な追加部分です。
データの受信中は、誤ったデータや通信の中断によってArduboy側がロックされてしまわないように、メインループから呼ばれて通信バッファが空(Serial.available()がゼロ)だった場合は必ずメインループへ戻ってボタン入力の処理を行うようにしています。

GUIは今回かなりたくさん書いた結果、ある程度スタイルができてきました。
コードはどう考えても現在のスタイルではなくOOPで書き直したほうが良いと思われますので、時間と意欲があればクラスライブラリ化したいところです。

現在重要な役割を担っているのは「process_button()」という関数で、ボタンの状態管理を行います。
引数は

・bool *state ・・・ 現在のボタンのオンオフ
・uint8_t *repeat_count ・・・ 長押し判定のためのカウンタ(処理不要の場合はNULL)
・uint8_t keycode ・・・ 処理対象のボタンの指定
・void(*release_func)() ・・・ ボタンを離したときの処理を行う関数
・void(*repeat_func)()) ・・・ 長押しのときの処理を行う関数
・返り値(bool) ・・・ 画面更新をする必要があるときはtrue

となっています。
例えば、Aボタンの処理はメインループの中で
process_button(&g_keystat.a, &g_keystat.a_repeat, A_BUTTON, a_released, a_long_press);

というようにコールしています。
a_releasedにAボタンが押されたときの処理、a_long_pressはAボタンが長押しされたときの処理を書きます。

ゲームと違って、GUIでは、ボタン操作への反応は押された時ではなく離された時に行うのが基本です。
反応の速さよりも、最後の最後までユーザに選択肢を残すことが重要だからです。
ラベル:Arduboy
posted by boochow at 18:53| Comment(0) | Arduino | このブログの読者になる | 更新情報をチェックする

2016年10月24日

FM音源をArduboyで動かしてみた


先々週、PWMを使ったシンセサイザをArduboyに移植しましたが、その記事の中でも触れたpcm1723さんの「FMMelody」をArduboyで動かしてみました。

基本的にはタイマー周りの設定をしてあげるだけで動作しました。
鳴らしてみると、圧電スピーカーでもはっきりと音色の違いが表れます。
FM音源は倍音成分が多いので、圧電スピーカー向きの音質なのかもしれません。

パラメータをいろいろいじって遊びたくなったので、パラメータ設定のGUIと、曲が一応変更可能なステップシーケンサーをArduboyで実装しました。
始めてみると、狭い画面にいかに詰め込むかに熱中してしまい、週末をつぶして一気に作成しました。
コードはこちらに置いてあります。

boochow/abSynth-FM: FM Synthesizer with step sequencer for Arduboy

動作させるには、「Arduboy2」ライブラリが必要です。
今回は、ユーザーインタフェースを作りながらコーディングしていったこともあり、コードはあまり綺麗ではありません。
機会があったら見直したいところです。

GUIは例によってpaint.netでお絵かきしながら考えました。
VSTiベースのソフトウェアシンセでよくあるような、見栄え重視のコントローラをイメージしました。

それを先日作ったツールでデータ化しています。
その静止画の上に線や小さなビットマップを上書きすることでGUIを作っています。
paint.netのようなお絵かきツールは、画像の中の座標が簡単に調べられるので、こういうコーディングをするときに便利です。

loopの中は一般的なArduboyのアプリケーションと若干違っていて、画面の書き換えが最小限になるようにしています。
画面周りの処理を重くすると音のほうがとぎれがちになるためです。

Arduboy、シーケンサー付きのシンセサイザーとしてはTeenage EngineeringのPOシリーズよりも小型軽量かもしれませんね。
オーディオアウトがあればチップチューン用に使えたかもしれません。
まあ、分解して線を引き出せば良いのですが。
下のビデオの方はたぶんそれをやっていると思います。


ちなみに分解写真が以下のスレッドにありますが、圧電ブザーの線を引き出すだけなら簡単にできそうです。

Kickstarter Edition numbering - General - Community
ラベル:Arduboy
posted by boochow at 01:50| Comment(0) | Arduino | このブログの読者になる | 更新情報をチェックする

2016年10月10日

ArduboyでのPWMサウンド出力

Arduinoのライブラリには標準でtone命令が用意されていますが、一定音量の矩形波しか出せません。
PWM(パルス幅変調)を使うと、アナログ波形を出力することができるので、より多彩な音を出すことができます。
I/Oピンからは1か0の信号しか出せないのですが、PWMは1と0を高速に出力して、その時間平均を取ることにより中間の値を表現します。

直感的には「白」と「黒」を交互に切り替える操作を高速に行うと、「灰色」に感じられる、というようなものです。時間軸に沿って「白」と「黒」を見せる割合を変化させると、「灰色」の濃さも変化させることができるわけです。

Arduboy内蔵のスピーカーでも、この機能は使えます。
圧電スピーカーなので再生能力は限定されますが・・・。


ということで、ちょっと関連の情報を調べてみたので整理しておきます。


まず、Arduino UNOではPWMを使った音声出力の実験がいろいろ行われています。

・FM音源
Arduino スケッチ 「FMmelody」
Pakurino (1) - シンセ・アンプラグド

・ポリフォニックサウンドジェネレータ
PWMDAC_Synthライブラリ | CAmiDion blog
PWMDAC_Synthライブラリ Wiki - OSDN

・解説記事ほか
[WIP] Arduinoで音を出したい(メモ) - Qiita
Audio via Arduino 16-bit PWM | Sand, software and sound
Secrets of Arduino PWM
TimerのPWMモードで Sin波形を発生
シグマデルタ変調 PWM (1) - シンセ・アンプラグド

これらの記事では実際に動作するスケッチやライブラリが紹介されています。
ただし、そのほとんどはArduino UNO用で、Arduboyにはそのままでは使えません。
ArduboyはArduino Leonardoベースであり、UNOのCPU(ATmega328)とは異なるCPU(ATmega32u4)が使われており、利用できるハードウェアタイマーが異なるためです。
以下に解説があります。

R6500: Fast PWM on Arduino Leonardo
Arduino Timer | TONYLABS

Arduino UNOおよびArduino Leonardoのピンアサイン図は以下にあります。

Arduino Pinout Diagrams – marcusjenkins.com

Arduino UNOでPWM出力できるピンは3, 5, 6, 9, 10, 11です。
ただし、上述のPWMDAC_Synthライブラリの作者さんによると、5と6が連動するTIMER0はArduino の millis() などのために使われているため、利用できないようです。

Arduino LeonardoPWM出力できるピンは3, 5, 6, 9, 10, 11, 12, 13となっています。
また、32u4はタイマー2が無く、タイマー3と4があります。

PWMで利用する、値比較(Output Compare)用のレジスタと出力ピンの関係について、UNOとLeonardoで対比すると以下のようになっています。

Timer 0 (8 bit)
・OC0A → UNO(6)、Leonardo(11)
・OC0B → UNO(5)、Leonardo(3, 18)
Timer 1 (16 bit)
・OC1A → UNO(9)、Leonardo(9)
・OC1B → UNO(10)、Leonardo(10)
・OC1C → UNO(-)、Leonardo(11)
Timer 2 (8 bit)
・OC2A → UNO(11)、Leonardo(-)
・OC2B → UNO(3)、Leonardo(-)
Timer 3 (16 bit)
・OC3A → UNO(-)、Leonardo(5)
Timer 4 (10 bit)
・OC4A → UNO(-)、Leonardo(13)
・OC4B → UNO(-)、Leonardo(10)
・OC4D → UNO(-)、Leonardo(6)
・#OC4A → UNO(-)、Leonardo(5)
・#OC4B → UNO(-)、Leonardo(9)
・#OC4D → UNO(-)、Leonardo(12)

なお、#OCnxは、OCnxのNOTで、かつOCnxの立ち上がりより前・立下がりより後に変化させることができるようです。このへんは詳しいことは良く分かりません。データシートには詳しく書かれています。
また、以下のサイトに日本語訳があります。

AVR.jp

AVRのタイマーに関しては、以下の解説も詳しいです。

AVRでのタイマとPWMの使い方 | うしこlog


ではArduboyはどのようなハードウェア設計になっているかですが、Arduboyの開発過程でも、PWMによる音声出力を想定してスピーカー周辺の設計(主に、どの出力ピンとタイマーを割り当てるか)については、相当に議論が行われていたようです。

Music library brainstorm - Arduboy / Development - Community

その結果、圧電ブザーはPC6(Arduino的には5番ピン)とPC7(Arduino的には13番ピン)の間に接続することになりました。
(下の引用した回路図はPD6につながっていますが、その後の議論でPC7に変わりました。なお、最終的な完全な回路図はこちら
arduboy-schematic.png

Arduboy Kickstarter version design discussion - Arduboy / Development - Communityより引用)

従って、Arduboyの圧電ブザーを鳴らす信号はタイマー3で作ることもできるし、タイマー3とタイマー4を組み合わせて使うこともできるし、タイマー4だけで作ることもできるようになっています。

もっとも、「Pin 6とPin 12にしておけば圧電ブザーから入力することもできたのに!」という意見も書かれていました。スピーカーは電力を運動(音波)に変換しますが、逆に音波を電力に変換することもできるので、ADC入力として使えるPin6を割り当てれば、音を拾えたかもしれないということのようです。


実際にPWMを使ってサウンド再生をするプログラムもいくつか作られています。
もっとも単純なものは、上記のコミュニティ議論の中でノコギリ波を生成するサンプルとして提示されているもので、25番目の書き込みにあります。
似たコードが二つ提示されていますが、1つ目はタイマー4のみ、2つ目はタイマー3とタイマー4を使って信号を生成しています。
タイマー4のみのほうが音量が大きめです。
タイマー4のみを使う場合はスピーカーの2つの端子に逆相の信号を与えられますが、タイマー3と4を使う場合は2つの信号が打ち消しあっているかもしれない、と記事のコメントには書かれています。

Music library brainstorm - Arduboy / Development - Community

また、Arduboy用にさまざまなゲームを作っているTEAM a.r.g.さんが4和音のライブラリを開発中です。現在はまだ完成版ではないようですが、ArduboyBasedTrackerというサンプルが動作しています。

[WIP] 4 channel Music - Arduboy / Development - Community

ということで、私も試しに上述のPWMDAC_SynthライブラリをArduboyに移植してみました。
出力は、とりあえず5番ピン側でタイマー3を使うことにしました。
オリジナルはタイマー1またはタイマー2を使用するようになっていますので、その部分をタイマー3に書き換えます。

6和音だと処理能力の余力が小さそうなので、4和音にしました。
ファイルは以下のGitHubに置いてあります。
動作させるには「Arduboy2」ライブラリが必要です。(Arduboy2はサウンド関連が分離されているため、競合が起こりません。)

boochow/pwmtest: PWM sound synthesize test for Arduboy

一応音は出るようになりましたが、結構小さい音です。
下のビデオではICレコーダーと重ねて録音レベルを最大にして録っていますが、それでもこの程度です。
ゲームの効果音に使うには、ちょっと迫力に欠けるかもしれません。



録音した音声の波形です。音声に強弱が付いていることが分かります。

pwmwave.png


2016/10/11追記:
タイマー4を使うコードも追加しました。やはりタイマー4のみのほうが音は大きいです。

スケッチの中で
#define PWMDAC_OUTPUT_PIN 13
#define PWMDAC_OUTPUT_PIN2 5

とするとタイマー4を使います。タイマー3を使う場合は、
#define PWMDAC_OUTPUT_PIN 5
#define PWMDAC_OUTPUT_PIN2 13

として下さい。
ラベル:Arduboy
posted by boochow at 01:48| Comment(0) | Arduino | このブログの読者になる | 更新情報をチェックする

2016年10月04日

スケッチファイルのフォルダの中にフォルダを作ってはいけないらしい

Arduino IDEは今まで1.6.9を使っていたのですが、1.6.12が出たのでそちらをインストールしてみました。
ところが、1.6.12で今開発中のabshellをコンパイルするとコンパイルが通りません。

調べてみると、スケッチの中にフォルダを作って入れてあったNT-Shellがコンパイルされておらず、リンクエラーになっていました。
1.6.9ではコンパイルできていたので、仕様が変わったようです。
テンポラリフォルダを調べると、ソースコード自体はディレクトリごとコピーされていましたが、コンパイルはされていませんでした。

ネットで情報を漁ってみても、どうやら「スケッチを入れるフォルダの中にサブディレクトリは作れない」というほうが常識のようです。(文句を言っている人も多いのですが)

もしかすると1.6.12のバグで、今後修正されるのかもしれませんが、待ってもいられないのでフォルダを無くしてファイルをすべてトップ階層に移動しました。
また、ついでにこれまでフラッシュに格納していなかった定数配列を3つほど、フラッシュ側へ移動しました。
これでRAM使用率は68%まで下がったので、安定動作が期待できそうです。
posted by boochow at 00:00| Comment(0) | Arduino | このブログの読者になる | 更新情報をチェックする
人気記事