2011年8月22日月曜日

CCNodeのdrawメソッドでOpenGL

cocos2dでCCSpriteをテクスチャーに描画する方法を調べていました。
Dr. Mandala のようなキャンバス系お絵かきソフトを cocos2d で作りたいと考えていたためです。

残念ながら、cocos2dのクラスリファレンスやネットを調べても、それらしい便利なメソッドは見つけられませんでした。
どうもそういう特殊用途のメソッドは、自分でOpenGL ESで実装するというのが正解みたいです。また、cocos2dのソースをちょっと見た限りでは、OpenGL ESを知っていればそう難しい事でもなさそうです。

今回調べて分かったことは、CCNodeクラスの -(void)draw メソッドをオーバーライドして、その中でOpenGL ESコマンドが書けるらしいということです。
テクスチャーへの描画はちょっと脇へ置いて、まずは、その辺りを最初に試してみることにしました。

お題は、背景にグラデーションのスプライトを敷くプログラムです。
新たに CCSpriteクラスを継承した、Bg クラスを作成しました。

ヘッダファイル抜粋
// Bg.h
@interface Bg : CCSprite {
}
+ (id)bg;
@end

実装ファイル抜粋
// Bg.m
@implementation Bg

+ (id)bg
{
	return [[[self alloc] init] autorelease];
}

- (void)draw
{
	// デフォルトでは以下のstateはEnableになっているので
	// このメソッドを去る時には、必ずEnableに戻しておかなければいけない。
	// - glEnableClientState(GL_VERTEX_ARRAY);
	// - glEnableClientState(GL_COLOR_ARRAY);
	// - glEnableClientState(GL_TEXTURE_COORD_ARRAY);
	// - glEnable(GL_TEXTURE_2D);
	// また、これ以外のstateはDisableに戻しておくこと。

	CGSize screenSize = [[CCDirector sharedDirector] winSize];	// スクリーンサイズ

	// シートを敷く
	const GLfloat vertices[] = {
		0,0,
		0,screenSize.height,
		screenSize.width,0,
		screenSize.width,screenSize.height,
	};
	const GLfloat colors[] = {
		1.0f,0.0f,0.0f,1.0f,
		0.0f,1.0f,0.0f,1.0f,
		0.0f,0.0f,1.0f,1.0f,
		1.0f,1.0f,0.0f,1.0f,
	};
	
	glDisableClientState(GL_TEXTURE_COORD_ARRAY);
	glDisable(GL_TEXTURE_2D);
	
	glVertexPointer(2, GL_FLOAT, 0, vertices);
	glColorPointer(4, GL_FLOAT, 0, colors);		// α値を含めたRGBAにしなければならないので、最初のパラメータは4
	glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
	
	glEnableClientState(GL_TEXTURE_COORD_ARRAY);
	glEnable(GL_TEXTURE_2D);
}
@end

あとは、Bgクラスをインスタンス化して、適当なシーンに追加するだけです。
Bg *bg = [Bg bg];
bg.position = CGPointZero;	// (0,0) は画面の左下
[myScene addChild:bg z:-1 tag:GameSceneNodeTagBg];

実行結果は下のような感じになります。
前回のテストプログラムから引き継いで、だいぶサイケになったネコ君でした。


0 件のコメント:

コメントを投稿

Related Posts Plugin for WordPress, Blogger...