リソースファイルからシステムに存在しない独自のTrueTypeフォントを読み込み、使用できるようにする方法。

§1 Windows 2000以降の場合

Windows 2000以降の場合はAddFontMemResourceExを使用することが出来、この場合次の手順でフォントを追加する。

  1. LoadResource, LockResourceでリソースファイルに埋め込んだフォントへのポインタを取得する
  2. AddFontMemResourceExにフォントへのポインタを渡して、フォントを追加する
  3. CreateFontで追加したフォントのハンドルを作成する
  4. 作成したフォントハンドルを使用して文字を描画するetc.
  5. 最後にRemoveFontMemResourceExで追加したフォントを削除する
// IDI_BINARY1は埋め込んだフォントのリソースID
HRSRC hFontResource = FindResource( hInstance, "IDI_BINARY1", "Binary");

LPVOID lpFontImage = LockResource( hFontResource );

DWORD dwFontImageSize = SizeofResource( NULL, hFontResource );

DWORD dwFontCount = 0;

HANDLE hFontResource = AddFontMemResourceEx( lpFontImage, dwFontImageSize, NULL, &dwFontCount );

if ( hFontResource )
{
    printf( "%d個のフォントを追加しました。", dwFontCount );
}

/*
CreateFontで追加したフォントのハンドルを作成、使用する
*/

RemoveFontMemResourceEx( hFontResource );

なお、登録したフォントは自プロセス内でのみ使用できる(他のプロセスからは参照できない)。 また、登録したフォントはプロセス終了時に自動的に解放されるので、プロセス終了時まで登録したフォントを使用する場合は必ずしもRemoveFontMemResourceExしなくても問題はない。

§2 Windows 2000より前のバージョンの場合

Windows 2000より前のバージョンでは、AddFontMemResourceExの代わりにAddFontResourceを使用できる。 この場合次の手順でフォントを追加する。

  1. LoadResource, LockResourceでリソースファイルに埋め込んだフォントへのポインタを取得する
  2. メモリ上にあるフォントのイメージをいったんファイルに書き出す
  3. CreateScalableFontResourceに書き出したファイルを渡し、フォントリソースファイルを作成する
  4. AddFontResourceにフォントリソースファイルを渡してフォントを追加する
  5. CreateFontで追加したフォントのハンドルを作成する
  6. 作成したフォントハンドルを使用して文字を描画するetc.
  7. RemoveFontResourceで解放する
  8. 作った一時ファイルを削除する

AddFontResourceではファイルとして存在するフォントしか登録できないため、リソースをいったんファイルとして書き出す必要がある。

// IDI_BINARY1は埋め込んだフォントのリソースID
HRSRC hFontResource = FindResource( hInstance, "IDI_BINARY1", "Binary");

LPVOID lpFontImage = LockResource( hFontResource );

DWORD dwFontImageSize = SizeofResource( NULL, hFontResource );

/*
LockResourceで取得したフォントイメージをいったんファイルに書き出す
*/

// 'PrivateFont.ttf'はリソースから書き出したフォントのファイル名
// 'PrivateFont.for'は作成するフォントリソースファイル名
if ( CreateScalableFontResource( 0, "PrivateFont.for", "PrivateFont.ttf", NULL ) )
{
    if ( AddFontResource( "PrivateFont.for" ) )
    {
        // フォントを登録したことを通知する
        SendMessage( HWND_BROADCAST, WM_FONTCHANGE, 0, 0 );
    }
}

/*
CreateFontで追加したフォントのハンドルを作成、使用する
*/

if ( RemoveFontResource( "PrivateFont.for" ) )
{
    // フォントを削除したことを通知する
    SendMessage( HWND_BROADCAST, WM_FONTCHANGE, 0, 0 );
}

/*
作成したファイル'PrivateFont.ttf', 'PrivateFont.for'を削除する
*/

フォントを追加・削除したら、SendMessageでフォントの変更を通知する必要がある。 なお、CreateScalableFontResourceの第一引数に0を指定した場合は、システム全体で有効なフォントとして登録される。 一方、1を指定した場合は自プロセスからのみ参照できるプライベートなフォントとして登録される。(ただし、1を指定してプライベートなフォントとして登録しても、CreateFontでフォントハンドルを作成して描画した文字は標準のフォントのものとなってしまう。 原因は不明。)

§3 .NET Frameworkを使用する場合

.NET Framework(1.0以降)では、System.Drawing.Text.PrivateFontCollectionを使用することで同様のことを実現できる。