表示結果:ただし、毎回エスケープ文字を入れてコードを書くのは少々面倒だし、実際のところArduinoIDEのシリアルモニタは性能が良くないので、外部の端末エミュレータを使用した方がよいと思います。外部の端末エミュレータを使用する場合の注意点は、端末側で繋ぎっぱなしにしているとArduinoIDEからプログラミングの書き込みができなくなるので、必ずプログラムの転送前には接続を切っておく必要があるというところくらいです。標準のシリアルモニタが転送前に毎回閉じるのもこの辺が理由。使うフォントデータについて使うフォントデータはFONTX形式を使用します。DOS上の日本語環境改善策として、日本の有志により作成されたフォントドライバで。このソフトウェア自体はDOS/V専用で今となっては無用のものとなりましたが。そのフォントドライバで扱われていたフォントファイルは、形式が単純で軽く、様々なフォントサイズのフォントが扱えるため当時のコンピュータやそれ以下の処理性能しか無いマイコンなどでフォントを扱う場合にもってこいのフォント形式なので最近人気が再燃しているようです。参考資料:FONTXの使いかた)FONTXファイルのフォーマット基本的に文字コードはShift_JISです。1バイト目から6バイトがファイルシグネチャ「FONTX2」が入っています。6バイト目から14バイト目までの8バイトにフォント名が入っています。この2つはマイコンにてフォントを扱う場合においては気にする必要はないでしょうし、扱うメモリも惜しいですので気にせずに14バイトシークしてしまいましょう。(若しくは最初から削っておくか)14バイト以降は「フォント幅・フォント高さ・文字コードフラグ」の順で記録されていて各データのデータサイズは1バイトとなっております。17バイト目はフォントの種類によって違い。半角文字用のフォント(コードフラグ0)の場合はここからフォントイメージが始まります。全角文字用のフォント(フォントフラグ1)の場合は17バイト目にはコードブロックの総数が格納れています。日本語の文字コードは2バイト文字で65536文字格納することが可能ですが。実際に利用されるのは7000文字程度なので、正直いって殆どの領域が無駄領域となっています。(ただしこれは一般的なフォントファイルはJIS第2水準漢字まで採用していることが多いためであり。Shift_JISの規格上はもう少し文字数は多いです。)そのため、FONTXでは、そのフォントが文字コードのどこからどこまでを収録しているものなのかを格納しておく領域が存在します。これをコードブロックと呼んでおります。半角フォントの場合はここからフォントデータが始まりますが。全角フォントの場合は先程説明したコードブロックのデータが続いております。2バイトコードですので開始コードと終了コード、計4バイトのデータがコードブロックの総数分記録されています。このフォントファイルのヘッダは以下のとおりとなっています。フォントイメージのについてフォントデータはBMP等と同様に横8ドット分が1バイトに収まっていて、例えば12ドットや10ドットのような8の倍数でない場合には8ビット(1バイト)単位で穴埋めされています。イメージまでのオフセット計算方法それでは、以上のフォーマットで目的の文字パターンが何処に格納されているのかをどうやって知ればいいのかというと。オフセットを計算すればいいわけですが。半角フォントと全角フォントで計算方法が微妙に違います。フォントのデータサイズの計算方法は以下のとおりです。文字コード×フォントサイズ8×16ドットのフォントファイルで、「S」の文字までのオフセットを計算する場合は、1フォントあたり16バイト、Sの文字コードは0x53(83)ヘッダーサイズは17バイトなので。1345バイトとなります。全角フォントの場合の計算式ヘッダサイズ+4×Cb+該当コードまでの文字数×フォントサイズ8×8ドットのフォントファイルで。「さ」の文字までのオフセットを計算する場合は、1フォント8バイト、「さ」の文字コードは82B3となります。コードブロックの総数はフォントの収録内容によって違いますが。何時も利用している美咲フォントのサイトにあるFONTX2形式のファイルの場合は92個のブロックに分かれています。次に該当コードまでの文字数の計算方法ですが。フォントブロックの終了コード-フォントブロックの開始コード+1で1ブロックあたりの文字数を計算して、該当文字コードがその範囲にない場合は次のブロックに進み、該当の文字コードが含まれるまで計算結果を累積していきます。「さ」の文字は82B3なので、11ブロック目に存在し、10ブロック目までに209文字存在することになり、11ブロック目の開始位置は829Fなので手前に20文字存在することになり、足すと229文字目が「さ」が格納されている文字になります。2218バイトとなります。上で説明したフォント形式の場合、半角の「S」なら1345バイト目から16バイト抜き出し、全角「さ」なら2218バイト目から8バイト抜き出せば目当ての文字が得られるということです。コーディングまずSDカードを使用するので標準ライブラリをインクルードし、defineでフォントファイルのファイル名を指定します。ファイルはSDカード直下に記録しています。次に上の説明を実現し、パターンを取得する関数を作ります。関数の詳しい説明はコメントに書いてあるのでそれを読んでください。FONTX形式のフォントファイルからフォントファイルを読み込み。最小8ドット四方・最大255ドット四方まで対応。最小フォントサイズは実用値、最大フォントサイズは論理値。1フォントあたりのバイト数以上を確保すること。2バイトの範囲内なら全角コード用のファイルを読み込む。フォントデータの読み込み。コードフラグが0なら英文フォント用のオフセットを書き込む。ブロック数のデータは2バイト用フォントにしか無いのでココで取得する。取得したブロック内に該当文字コードが存在しない場合。存在しなかったブロック内の文字数を計算して次へ。FONTX形式のフォントファイルからフォントファイルを読み込み。最小8ドット四方・最大255ドット四方まで対応。最小フォントサイズは実用値、最大フォントサイズは論理値。1フォントあたりのバイト数以上を確保すること。2バイトの範囲内なら全角コード用のファイルを読み込む。フォントデータの読み込み。コードフラグが0なら英文フォント用のオフセットを書き込む。ブロック数のデータは2バイト用フォントにしか無いのでココで取得する。取得したブロック内に該当文字コードが存在しない場合。存在しなかったブロック内の文字数を計算して次へ。;}この関数の動作は受け取った文字コードの数値により使用フォントを決定256以下なら半角用フォント、それ以上なら全角用フォントを呼び出すフォントファイルを14バイトシークヘッダである文字サイズ縦・横、文字コードを取り出す取り出した文字サイズからデータサイズを計算するフォントタイプによって条件を分岐する半角フォントならオフセットを計算。全角フォントの場合は、ブロック総数のデータを取得し該当文字が格納されているブロックが見つかるまでブロック内の文字数を控えつつループ、見つかったらオフセットを計算。計算されたオフセット分ファイルをシークするそこからフォントのデータサイズ分フォントデータを配列に読み出すフォントファイルを閉じる戻り値を返して完了。戻り値はフォントが見つからない場合は0を返す。longのデータに「フォント幅(1)」「フォント高さ(1)」「データサイズ(2)」を連結させて返す。24×18ドットのフォントの場合はデータサイズは54バイトで「0x18120036」が戻り値となり、これをビット演算で切り出すことで目的の値が取得できる。いう動作になっている。long型が必要となります。);記述すれば使用することが出来ます。Arduinoのシリアル通信は1バイトずつ取得できますので、文字コードの受信は以下のとおりに行います。8;}最初に8bitシフトして1バイト目を取得します。そのコードが2バイト文字を扱う範囲にあるかどうかを確認し、2バイト文字の上位バイトだった場合は、2バイト目を続けて取得します。1バイト文字と判断された場合は、最初にシフトした8bitを戻して終了します。戻り値ですが、フォント幅を取得する場合は24bitシフトして0xFFでマスクをして抜き出します。フォントの高さは16bitシフトしてマスクします。データサイズを取得する場合はビットシフトは不要で0xFFFFのマスクをかけるだけで取得できます。最後に掲載しているサンプルコードを実行して「桜」の文字を送信すると以下のようになるはずです。(文字コードはShift_JISです。)終わりにArduinoで使う場合は漢字ROMを使う以外では最良の方法だと思います。Piに関しても、多分この方法のほうが早いです。いうわけで今回はフォントファイルから漢字パターンを取得する方法をご紹介しました。これを使えば8×8ピクセル以外に12×12や16×16、もっと大きなフォントも使えるので例えばカラー液晶などに転送する場合はこっちの方がいいでしょうね。この文字コードは縦はドット分そのままですが、横が8ドット単位で格納されています。14ドットなどの場合は2pxの空きとなるので逆に見やすいですが。10pxや12pxの場合はちょっと文字間が開きすぎなので、文字を転送し終えたあと例えば12ドットなら4ドット分戻って次の文字を転送すると穴埋め分をかき消すことができると思います。準備ができたら「準備完了!」と送信。ArduinoIDEのシリアルモニタはShift_JISなのでエスケープ文字をつけて文字コードを送信してやる。FONTX形式のフォントファイルからフォントファイルを読み込み。最小8ドット四方・最大255ドット四方まで対応。最小フォントサイズは実用値、最大フォントサイズは論理値。1フォントあたりのバイト数以上を確保すること。2バイトの範囲内なら全角コード用のファイルを読み込む。フォントデータの読み込み。コードフラグが0なら英文フォント用のオフセットを書き込む。ブロック数のデータは2バイト用フォントにしか無いのでココで取得する。取得したブロック内に該当文字コードが存在しない場合。存在しなかったブロック内の文字数を計算して次へ。それに合わせて穴埋めする。戻り値からフォントサイズのみ抜き出す。改行位置が違う以外は前回のものと同じ。動いてないのか範囲外のコードなのかわからないので範囲外のコードはエラーを返すようにする。準備ができたら「準備完了!」と送信。ArduinoIDEのシリアルモニタはShift_JISなのでエスケープ文字をつけて文字コードを送信してやる。FONTX形式のフォントファイルからフォントファイルを読み込み。最小8ドット四方・最大255ドット四方まで対応。最小フォントサイズは実用値、最大フォントサイズは論理値。1フォントあたりのバイト数以上を確保すること。2バイトの範囲内なら全角コード用のファイルを読み込む。フォントデータの読み込み。コードフラグが0なら英文フォント用のオフセットを書き込む。ブロック数のデータは2バイト用フォントにしか無いのでココで取得する。取得したブロック内に該当文字コードが存在しない場合。存在しなかったブロック内の文字数を計算して次へ。それに合わせて穴埋めする。戻り値からフォントサイズのみ抜き出す。改行位置が違う以外は前回のものと同じ。動いてないのか範囲外のコードなのかわからないので範囲外のコードはエラーを返すようにする。2つの記事を統合・加筆しました。コメントをキャンセルメールアドレスが公開されることはありません。コメントデータの処理方法の詳細はこちらをご覧ください。252ヴィッツ(NSP130)にナビ取り付けました。186DAC買いました。158スピーカー買いました。7年ぶりにメインのカメラを買い換えました。89キーボード買いました。テレビ台をDIYする。