2Dと3Dの合成時の処理
ここでは、BREW API を用いた 2D描画と3D描画との合成処理について解説します。
目次
MascotCapsule V4 (V3互換)やV4 では 2D描画と 3D描画を同一のフレームバッファに描画する方法でのみ 2D3D 合成が実現可能ですが (詳細はこちらをご覧下さい)、この方法は、パフォーマンスに影響が出ることから eruption では推奨しておりません。
代わりに、任意のフレームバッファに 2D を描画し、そのフレームバッファから生成された mceTexture と 3Dモデルを描画することで 2D3D合成を実現する実装を推奨しております。 実装法は以下の順になります。
- アプリ側で 2D 描画用のフレームバッファを作成
- 2D をフレームバッファへ描画
- mceTexture の生成
- mceTexture と3D モデルの描画
各実装の詳細については以下で説明します。
なお、本サンプルでは2D描画に日本語文字列を用います。
1. 文字列描画用のフレームバッファを作成
文字列描画用の任意のフレームバッファを作成します。作成の際は IBITMAP_CreateCompatibleBitmap( po, ppIBITmap, w, h ) を用いてデバイスビットマップと互換性のあるフレームバッファを作成します。
#define REGION_W (256) /* 矩形転送X軸サイズ */
#define REGION_H ( 64) /* 矩形転送Y軸サイズ */
typedef struct tagWork
{
(中略)
AEEApplet Applet; /* アプレット構造体 */
(中略)
} WORK;
IDIB* ComDib;
IBitmap* Combitmap;
IBitmap* Devbitmap; /* デバイスビットマップ */
int i_ret;
(中略)
/* デバイスビットマップの取得 */
i_ret = IDISPLAY_GetDeviceBitmap (work->Applet.m_pIDisplay,
&Devbitmap);
if (i_ret != SUCCESS)
{
return 1;
}
/* Devbitmap に互換性のあるビットマップの生成 */
i_ret = IBITMAP_CreateCompatibleBitmap (Devbitmap, &Combitmap,
REGION_W, REGION_H);
if (i_ret != SUCCESS)
{
return 1;
}
IBITMAP_Release (Devbitmap);
/* CombitmapをDIBに変換 */
i_ret = IBITMAP_QueryInterface (Combitmap, AEECLSID_DIB,
(void **)&ComDib);
if (i_ret != SUCCESS)
{
return 1;
}
2. 文字列をフレームバッファへ描画
文字列をフレームバッファに描画する際には、描画前に IDISPLAY_SetDestination( po, pDst ) を用いて作成したフレームバッファをレンダリングターゲットに設定する必要があります。また描画後には、IDISPLAY_SetDestination( po, pDst ) の第 2 引数を NULL に指定し、フレームバッファをレンダリングターゲットから外します。
#define REGION_W (256) /* 矩形転送X軸サイズ */
#define REGION_H ( 64) /* 矩形転送Y軸サイズ */
typedef struct tagWork
{
(中略)
AEEApplet Applet; /* アプレット構造体 */
(中略)
} WORK;
IBitmap *Combitmap;
AECHAR AEtext[18];
AEERect rect;
Int i_ret;
(中略)
/* 描画範囲の設定 */
rect.x = 0;
rect.y = 0;
rect.dx = REGION_W;
rect.dy = REGION_H;
(中略)
/* レンダリングターゲットの設定 */
i_ret = IDISPLAY_SetDestination (work->Applet.m_pIDisplay,
Combitmap);
if (i_ret != SUCCESS)
{
return 1;
}
IDISPLAY_FillRect (work->Applet.m_pIDisplay, &rect, 0x00000000);
i_ret = IDISPLAY_DrawText (work->Applet.m_pIDisplay,
AEE_FONT_BOLD, AEtext, -1, NULL, NULL, &rect,
IDF_ALIGN_CENTER | IDF_ALIGN_MIDDLE | IDF_TEXT_TRANSPARENT);
if (i_ret != SUCCESS)
{
return 1;
}
/* フレームバッファをレンダリングターゲットから外す */
i_ret = IDISPLAY_SetDestination (work->Applet.m_pIDisplay, NULL);
if (i_ret != SUCCESS)
{
return 1;
}
3. mceTexture の生成
文字列を描画したフレームバッファから mceTexture を生成します。
mceTexture_create( gID, format, width, height, useMipmap, exception ) で mceTexture を生成し、mceTexture_setImage( This, format, level, xp, yp, width, height, image ) を用いて生成した mceTexture にフレームバッファのピクセル情報を設定します。
#define REGION_W (256) /* 矩形転送X軸サイズ */
#define REGION_H ( 64) /* 矩形転送Y軸サイズ */
typedef struct tagWork
{
(中略)
AEEApplet Applet; /* アプレット構造体 */
(中略)
mceTexture* RegionTexture; /* RegionTexture */
(中略)
} WORK;
IDIB* ComDib;
IBitmap* Combitmap;
hi_uint32 format;
hi_exception exception;
Int i_ret;
(中略)
format = mcePixelFormat_RGB565; /* ピクセルフォーマット */
(中略)
/* 2D描画用テクスチャの生成 */
work->RegionTexture = mceTexture_create (0, format, REGION_W, REGION_H,
HI_FALSE, &exception);
if (exception != hi_NoException)
{
return 1;
}
/*フレームバッファのピクセル情報を2D描画用テクスチャに設定*/
exception = mceTexture_setImage (work->RegionTexture, format, 0, 0, 0,
REGION_W, REGION_H, (hi_sint8*)ComDib->pBmp);
if (exception != hi_NoException)
{
return 1;
}
IBITMAP_Release (Combitmap);
IQI_Release ((IQueryInterface *)ComDib);
ComDib = NULL;
4. mceTexture と 3Dモデルの描画
作成した mceTexture と 3Dモデルを描画します。
mceTexture の描画はリージョン機能である mceGraphics3D_drawRect( This, x, y, width, height, roll, abgr, appearance, regions, regionNum ) で行い、3Dモデルの描画は mceGraphics3D_drawFigure( This, figure, transform, param ) で行います。
また、mceTexture は 3Dモデルの背面と前に描画しますが、mceGraphics3D_drawRect() を使用すると mceTexture はデフォルトで最前に描画されてしまいます。そのため、3Dモデルの背面に mceTexture を描画する場合には、mceTexture を先に描画した後に、mceGraphics3D_clear( This, flag, abgr ) の第2引数に MCE_GRAPHICS3D_CLEAR_DEPTH を指定し、デプス値をクリアしてから 3Dモデルを描画するようにしてください。
なお、リージョン機能や 3Dモデルの描画については、それぞれ「リージョン」、「3Dモデルの描画」のドキュメントページを参照してください。
#define COORD_SHIFT (16) /* int→hi_coordのシフト */
(中略)
#define ANGLE (360) /* 角度 */
(中略)
#define REGION_W (256) /* 矩形転送X軸サイズ */
#define REGION_H ( 64) /* 矩形転送Y軸サイズ */
#define HEGHT_OFFSET ( 10) /* 矩形描画位置のオフセット値 */
typedef struct tagWork
{
(中略)
AEEApplet Applet; /* アプレット構造体 */
(中略)
mceGraphics3D *G3d; /* Graphics3D */
(中略)
hi_uint16 WindowWidth; /* 画面幅 */
hi_uint16 WindowHeight; /* 画面高さ */
(中略)
mceAppearance* RegionAppe; /* RegionAppearance */
mceRegionF Region; /* Region */
hi_coord ReZoom; /* 矩形転送拡縮率 */
hi_coord ReRotate; /* 矩形転送回転値 */
hi_coord ObjRy; /* オブジェクトY軸回転 */
(中略)
} WORK;
hi_exception exception;
mceTransform matrix;
mceTransform matrix2;
mceVector3D rotate;
hi_sint16 x, y, w, h;
(中略)
/*------ 2D描画 Back ------*/
/* 描画範囲設定 */
w = ((REGION_W * work->ReZoom) >> COORD_SHIFT);
h = ((REGION_H * work->ReZoom) >> COORD_SHIFT);
x = (work->WindowWidth / 2) - (w / 2);
y = HEGHT_OFFSET;
/* テクスチャ描画 */
exception = mceGraphics3D_drawRect (work->G3d, x, y, w, h,
work->ReRotate / ANGLE, 0xffffffff,
work->RegionAppe, &work->Region, 2);
if (exception != hi_NoException)
{
return 1;
}
/* デプス値のクリア */
exception = mceGraphics3D_clear (work->G3d,
MCE_GRAPHICS3D_CLEAR_DEPTH, 0x00808080);
if (exception != hi_NoException)
{
return 1;
}
/*------ 3D描画 ------*/
mceTransform_setTranslate (&matrix, MCE_F2C (0.0f), MCE_F2C (0.0f),
MCE_F2C (0.0f));
mceVector3D_set (&rotate, MCE_F2C (0.0f), MCE_F2C(1.0f),
MCE_F2C (0.0f));
mceTransform_setRotate (&matrix2, &rotate, work->ObjRy / ANGLE);
mceTransform_multiply (&matrix, &matrix2);
/* モデルの描画 */
exception = mceGraphics3D_drawFigure (work->G3d, work->Figure,
&matrix, 0);
if (exception != hi_NoException)
{
return 1;
}
/*------ 2D描画 Front ------*/
/* 描画範囲指定 */
w = ((REGION_W * work->ReZoom) >> COORD_SHIFT);
h = ((REGION_H * work->ReZoom) >> COORD_SHIFT);
x = (work->WindowWidth / 2) - (w / 2);
y = work->WindowHeight - (REGION_H + HEGHT_OFFSET);
/* テクスチャの描画 */
exception = mceGraphics3D_drawRect (work->G3d, x, y, w, h,
work->ReRotate / ANGLE, 0xffffffff,
work->RegionAppe, NULL, 0);
if (exception != hi_NoException)
{
return 1;
}
/*------ 描画処理 ------*/
exception = mceGraphics3D_flush (work->G3d);
if (exception != hi_NoException)
{
return 1;
}
![]() |
|
| 描画結果 |


