● ToolBox API徒然草(2007/02/04)

  このニュースは、MOSAの会員にのみ配布されているデベロッパー向けの
  デジタルマガジンMOSADeNのに掲載された記事です。ほぼ一ヶ月遅れで
  ここに掲載されて行きます

 〜 Carbonモダンアプリケーションへの道(その8) 〜


前回は、ユニコード文字列を操作するAPIの特徴や利用方法などを取り上げてみました。その中で、Localizable.stringsの活用方を解説しましたが、そのサンプルの返す文字列中に「%1$@」といった変わった表記をみかけました。これは、どんな意味を持つのでしょうか? 今回は、こうした表記の仕組みを解説してみます。

前回のLocalizable.stringsサンプルの一行を再度見てみます。

VersionFormat = "%1$@ (%2$@)"; // for example, "4.0d8 (150)"

横のコメントには"4.0d8 (150)"と記述されていますので、バージョン番号を表記するためのフォーマットであることが分かります。つまり、%1$@には"4.0d8"が、%2$@には"150"が入ることになります。もうお気づきだと思いますが、%1$@や%2$@は、文字列中に別の文字列や数値を挿入するための書式変換フォーマットです。これと同様な仕組みで有名なものは、printf()で用いられる%d(整数の引数用)や%f(浮動小数点の引数用)といった書式変換フォーマットです。

%1や%2が引数の順番を示し、その後の$@がどんな種類の物を挿入するのかを表しています。ちなみに、$@はCore Foundation Frameworkで用いられているオブジェクトを指しており、文字列を参照するCFStringRefなどもこれに相当します。つまり、CFStringRefを渡すことでオリジナル文字列に別の文字列を挿入することなどが可能なのです。こうした書式変換フォーマットを含んだ文字列を自作アプリケーション内で活用するには、前回紹介したFCopyLocalizedString()と、以下のCFStringCreateWithFormat()を同時に用います。



NULLを代入することで1番目のと2番目の引数は省略できます。先んじてCFStringRefとして定義しておいたcfstr2に"4.0d8"が、cfstr3の方には"150"が代入されているとすると、上記サンプル行のバージョン文字列を得るには以下のように記述すればOKです。これで、cfstrに目的のバージョン文字列が返ります。

cfstr1=CFCopyLocalizedString( CFSTR( "VersionFormat" ),"" );
cfstr=CFStringCreateWithFormatAndArguments( NULL,NULL,cfstr1,cfstr2,cfstr3 );

文字列の代わりに整数値などを挿入する場合には、$@の代わりに$dを用います。

PRINT_PAGE="%1$d/%2$d ページ";
PRINT_MONTH="%1$d 月度";

書式変換フォーマットに関する仕様は、ほとんどprintf()と同じであり、詳細についてはApple社が提供しているドキュメント「String Programming Guide for Cocoa」に詳しく載っていますので、そちらを参照してみてください。

「String Programming Guide for Cocoa」

http://developer.apple.com/documentation/Cocoa/Conceptual/Strings/Strings.pdf

続いてサンプルルーチンを幾つか紹介しておきます。最初は、Cストリングスとしてキーワードを渡し、Localizable.stringsに定義されている文字列を得るルーチンです。その次は、CFStringRefをユニコード文字列に変換してから返すルーチンです。以前紹介した自作のcToCFString()やcfToUnicodeString()ルーチンを活用しています。



また、文字列中に整数値(変数として)をひとつだけ挿入したい場合があります。以下の例では、1から12のどれかの整数値を挿入して「1 月度」や「12 月度」という文字列を生成したいわけです。

PRINT_MONTH="%1$d 月度";

こんな場合には、CFStringCreateWithFormat()に整数値をひとつだけ渡すルーチンを作成しておけば便利です。



それから、先ほどの例において%1$@と%2$@に代入する文字列もLocalizable.stringsに登録されているとすると...

VersionFormat = "%1$@ (%2$@)";

次のようなルーチンで対応することができます。



次回は、こうして入手した文字列をウィンドウに表示したりプリントアウト(印刷)したりする状況を考えてみます。昔であれば、QuickDraw APIのDrawString()などを用いれば簡単でしたが、モダンアプリケーションではいったい何を使えば最良なのでしょうか?


copyright 2007 Ottimo, Inc. All rights reserved
無断転載・引用禁止