先日、久しぶりにAndroid版の東方VGSをアップデートしてみたら、立て続けに2件ほど「アルバムタイトルが表示されなくなった」という報告がレビューで挙ってきました。
どうやら報告は両方ともAndroid 5らしいです。
私はAndroid 5の端末を持っていない(&私の手持ちのAndroid 4.4の端末では再現しない)ので、知り合いが偶然持っていたNexus 5 + Android 5の端末で動かしてみたところ現象を確認。
通常だと、下図のように表示されるはずのところ、
以下のような感じで表示されていました。
そもそも、このタイトル表示は通常のAndroidのTextViewではなく、割と特殊な方法で表示しています。
まず、GitHubの方でも公開している titlelist.txt というテキストファイル(CSVファイル)をSJISに変換したものから以下の形式の構造体を生成していて、それをromdata.binの中に突っ込んでいます。
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* title data */ | |
struct TitleData { | |
int id; | |
int songNum; | |
char copyright[32]; | |
char title[80]; | |
char reserved2[8]; | |
}; |
※1タイトルにつき1インスタンス
そして、それを以下のようにputkanjiという関数で表示
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/* Draw song title */ | |
putkanji(4 + bx, 134 + (int)base, 255, _title[ct].title); | |
putkanji(236 + bx - ((int)strlen(_title[ct].copyright)) * 4, 152 + (int)base, 255, _title[ct].copyright); | |
if (_title[ct].id == 0x60) { | |
putkanji((240 - (((int)strlen(_msg)) * 4)) / 2 + bx, 40 + (int)base, 255, "%s", _msg); | |
} |
putkanjiはこんな感じ
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
static unsigned short getcode(unsigned char sjis[2]) | |
{ | |
unsigned char jis[2]; | |
unsigned short ret; | |
jis[0] = sjis[0]; | |
jis[1] = sjis[1]; | |
if (jis[0] <= 0x9f) { | |
jis[0] -= 0x71; | |
} else { | |
jis[0] -= 0xb1; | |
} | |
jis[0] *= 2; | |
jis[0]++; | |
if (jis[1] >= 0x7F) { | |
jis[1] -= 0x01; | |
} | |
if (jis[1] >= 0x9e) { | |
jis[1] -= 0x7d; | |
jis[0]++; | |
} else { | |
jis[1] -= 0x1f; | |
} | |
ret = (jis[0] - 0x21) * 94; | |
ret += jis[1] - 0x21; | |
return ret; | |
} | |
static void putkanji(int x, int y, int col, const char* msg, ...) | |
{ | |
char buf[256]; | |
int i, j, k; | |
unsigned char c[2]; | |
int jis; | |
unsigned char bin; | |
va_list args; | |
va_start(args, msg); | |
vsprintf(buf, msg, args); | |
va_end(args); | |
for (i = 0; '\0' != (c[0] = (unsigned char)buf[i]); i++) { | |
if (c[0] & 0x80) { | |
c[1] = (unsigned char)buf[i + 1]; | |
jis = (int)getcode(c); | |
jis *= 12; | |
for (j = 0; j < 12; j++) { | |
bin = _kanji[jis + j]; | |
for (k = 0; k < 8; k++, bin <<= 1) { | |
if (bin & 0x80) { | |
vge_pixelSP(x + k, y + j, col); | |
} | |
} | |
} | |
x += 8; | |
i++; | |
} else { | |
c[0] -= 0x20; | |
vge_putSPM(255, c[0] % 16 * 4, c[0] / 16 * 12, 4, 12, x, y, col); | |
x += 4; | |
} | |
} | |
} |
・曲のタイトルは問題なく表示されているのでputkanjiはバグっていない。
・タイトルは表示されていないが「(c)2008」という ASCII コードのみの部分は表示されている
・また、IDは正常に引けている
・つまり、TitleDataのレコード自体はある
という点から文字コードのMBCS部分がデータ破損しているか \0 になっているんじゃないかと思うかもしれませんが、それなら私のAndroid 4.4でも問題なく表示される筈がないのでそれは無いです。
Android 5って実はOSのネイティブ周りの実装が結構強かに変更されているので、OS側のバグを踏んでしまったと考えるのが一番自然ですかねぇ。(この手の問題の原因としてよくあるのがグローバル領域を壊す系だろうか)
さて、どうしたものか。
Android版はバックグラウンド音飛びの件もあるし、公開停止してiPhone版一本で行くのも良いんじゃないだろうかというのが本音なのですが。(要約するとAndroidはもう嫌だ...ということ)
【追記】
エミュレータで現象を再現でき、原因も特定できたので、対策しました。
https://github.com/suzukiplan/Touhou-VGS-MML-data/pull/81
0 件のコメント:
コメントを投稿
注: コメントを投稿できるのは、このブログのメンバーだけです。