現在地メニュー >> Cg >> Cg編07 >> Cg編07::まとめ

問題


キューブマップ用の画像を読み込んで、キューブマッピングを行え

答え

vertex.cg

//入力頂点
struct VertexIn
{
	float4 position : POSITION;
	float3 color : COLOR;
};

//出力頂点
struct VertexOut
{
	float4 position : POSITION;
	float3 color : COLOR;
	float3 texcoord : TEX0;
};

//-------- 頂点シェーダメイン関数 ---------//
VertexOut CgVertexMain(in VertexIn input,
					   uniform float4x4 modelViewProj,
					   uniform float rotAngle)
{
	//度数→ラジアン
	float radAngle = radians(rotAngle);
	float SinData,CosData;
	
	sincos(radAngle,SinData,CosData); //sin(angle)とcos(angle)を計算しそれぞれ格納


	VertexOut output;//出力用

	output.position[0] = CosData*input.position[0] + SinData*input.position[2];
	output.position[1] = input.position[1];
	output.position[2] = -SinData*input.position[0] + CosData*input.position[2];
	output.position[3] = input.position[3];


	//回転移動したものを透視投影
	output.position = mul(modelViewProj, output.position);

	output.color = input.color;//色
	output.texcoord = input.position.xyz;

	return output;
}

fragment.cg

//フラグメントの入力
struct FragmentIn
{
	float4 position : POSITION; //ラスタライズ用(使用しない)
	float3 color : COLOR;
	float3 texcoord : TEX0;//(x,y,z)
};

//フラグメントの出力
struct FragmentOut
{
	float3 color : COLOR;
};

//--------- フラグメントシェーダメイン関数 ------------//
FragmentOut CgFragmentMain(in FragmentIn input,uniform samplerCUBE cubeDecal)
{
	FragmentOut output;//フラグメント出力
	
	output.color = texCUBE(cubeDecal,input.texcoord);
	return output;
}

main.cg

#include <iostream>
#include <gl/glew.h>//未定義トークン使用のため
#include <gl/glut.h>
#include <cv.h>
#include <cxcore.h>
#include <highgui.h>
#include <Cg/cg.h>
#include <Cg/cgGL.h>

#pragma comment (lib,"cg.lib")
#pragma comment (lib,"cgGL.lib")
#pragma comment (lib,"cv200.lib")
#pragma comment (lib,"cxcore200.lib")
#pragma comment (lib,"highgui200.lib")

//画像ファイル
const char *filename[]={"posx.jpg","negx.jpg","posy.jpg","negy.jpg","posz.jpg","negz.jpg"};
//テクスチャID
GLuint texId;


GLUquadricObj *quadric;

//-------- 各種外部変数 -------------//
//Cg用変数
CGcontext CgContext; //コンテキスト
CGprofile CgVertexProfile;//頂点プロファイル
CGprogram CgVertexProgram;
CGprofile CgFragmentProfile;//フラグメントプロファイル
CGprogram CgFragmentProgram;
CGparameter CgModelViewProj; //CGparameter型(ModelProj行列を取得)
CGparameter CgVertexRotAngle;//頂点シェーダ回転角度
CGparameter CgFs_CubeDecal;


//-------- プロトタイプ宣言 -----//
void display();
void reshape(int w, int h);
void drawXYZ();

//-------- Cgの初期設定 -----------//
//頂点シェーダ設定
void setUpCgVertex()
{
	//プロファイルの取得
	CgVertexProfile = cgGLGetLatestProfile(CG_GL_VERTEX);
	if(CgVertexProfile == CG_PROFILE_UNKNOWN)
	{
		std::cerr << "Invalid profile type\n";
		exit(0);
	}
	cgGLSetOptimalOptions(CgVertexProfile);


	//ファイルを読んでコンパイル
	CgVertexProgram 
		= cgCreateProgramFromFile(
			CgContext,//コンテキスト
			CG_SOURCE,//Cgソースコード
			"vertex.cg", //「.cgファイル名」
			CgVertexProfile, //プロファイル
			"CgVertexMain", //「.cgファイル」で最初にいく関数
			NULL); //NULLでよい

	cgGLLoadProgram(CgVertexProgram);//プログラムのロード
	if(CgVertexProgram==NULL){
		std::cerr <<"Vertex Program Err. \n";
		exit(0);
	}

	//パラメータの関連付け
	CgModelViewProj = cgGetNamedParameter(CgVertexProgram, "modelViewProj");
	CgVertexRotAngle = cgGetNamedParameter(CgVertexProgram, "rotAngle");

}

//フラグメントの初期設定
void setUpCgFragment()
{
	//プロファイルの取得
	CgFragmentProfile = cgGLGetLatestProfile(CG_GL_FRAGMENT);
	if(CgFragmentProfile == CG_PROFILE_UNKNOWN){
		std::cerr << "Fragment : profile is unknown\n";
		exit(0);
	}
	cgGLSetOptimalOptions(CgFragmentProfile);

	//プログラムのコンパイル
	CgFragmentProgram 
		= cgCreateProgramFromFile(
			CgContext,//コンテキスト
			CG_SOURCE,//Cgソースコード
			"fragment.cg", //「.cgファイル名」
			CgFragmentProfile, //プロファイル
			"CgFragmentMain", //「.cgファイル」で最初にいく関数
			NULL); //NULLでよい

	cgGLLoadProgram(CgFragmentProgram); //プログラムのロード
	if(CgFragmentProgram==NULL){
		std::cerr <<"Fragment Program Err. \n";
		exit(0);
	}

	CgFs_CubeDecal = cgGetNamedParameter(CgFragmentProgram, "cubeDecal");
	cgGLSetTextureParameter(CgFs_CubeDecal, texId); //テクスチャとの関連付け
}

void CgINIT()
{
	//コンテキスト作成
	CgContext = cgCreateContext();
	if(CgContext == NULL){
		std::cerr << "Can't Create Context\n";
		exit(0);
	}

	setUpCgVertex();
	setUpCgFragment();

}

void idle()
{
	glutPostRedisplay();
}

//------------ GLUTの初期設定 ---------------//
void GLUT_CALL_FUNC()
{
	glutDisplayFunc(display);
	glutReshapeFunc(reshape);
	glutIdleFunc(idle);
}

void OtherMyInit()
{
	glClearColor(1,1,1,1);
	glEnable(GL_DEPTH_TEST);
	quadric = gluNewQuadric();
	gluQuadricDrawStyle(quadric,GLU_FILL);
	gluQuadricNormals(quadric,GLU_SMOOTH);
	gluQuadricTexture(quadric,GLU_TRUE);

}

//テクスチャ読み込み
void LoadTexture()
{
	GLenum cubefaces[6] = {
		GL_TEXTURE_CUBE_MAP_POSITIVE_X,
		GL_TEXTURE_CUBE_MAP_NEGATIVE_X,
		GL_TEXTURE_CUBE_MAP_POSITIVE_Y,
		GL_TEXTURE_CUBE_MAP_NEGATIVE_Y,
		GL_TEXTURE_CUBE_MAP_POSITIVE_Z,
		GL_TEXTURE_CUBE_MAP_NEGATIVE_Z
	};

	//6つを1つにまとめて扱う事ができる
	glGenTextures(1,&texId);
	glBindTexture(GL_TEXTURE_CUBE_MAP,texId);
	glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
	glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_NEAREST);

	cv::Ptr<IplImage> imgA;
	for(int loop = 0;loop < 6;++loop)
	{
		imgA = cvLoadImage(filename[loop]);
		if(imgA.empty())
		{
			std::cerr << filename[loop] << " : Can't Load Image\n";
			exit(EXIT_FAILURE);
		}

		glTexImage2D(cubefaces[loop],0,GL_RGB,imgA->width,imgA->height,0,GL_BGR,GL_UNSIGNED_BYTE,imgA->imageData);
		imgA.release();
	}

	glBindTexture(GL_TEXTURE_CUBE_MAP,0);
}


void GLUT_INIT(int argc,char **argv)
{
	glutInit(&argc,argv);
	glutInitDisplayMode(GLUT_RGBA | GLUT_DOUBLE | GLUT_DEPTH);
	glutInitWindowSize(640,480);
	glutCreateWindow("simple animation");
	GLUT_CALL_FUNC();
	OtherMyInit();
	LoadTexture();
	
}

//---------- メイン関数 ---------------//
int main(int argc,char **argv)
{
	GLUT_INIT(argc,argv);
	CgINIT();//Cgセットアップ


	glutMainLoop();

	return 0;
}



//----------- ここから各種コールバック -----------------//
void display()
{
	static int angle = 0;
	glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
	glLoadIdentity();

	gluLookAt(2,3,5,0,0,0,0,1,0);


	//Cgの有効化
	cgGLBindProgram(CgVertexProgram);
	cgGLEnableProfile(CgVertexProfile);

	cgGLBindProgram(CgFragmentProgram);
	cgGLEnableProfile(CgFragmentProfile);

	cgGLEnableTextureParameter(CgFs_CubeDecal);//テクスチャのバインド
	
	cgSetParameter1f(CgVertexRotAngle, static_cast<float>(angle)); //GPUで使う回転角度値の設定

	//現在のmodelview,projection行列を取得
	cgGLSetStateMatrixParameter(
		CgModelViewProj,
		CG_GL_MODELVIEW_PROJECTION_MATRIX,
		CG_GL_MATRIX_IDENTITY);

	cgUpdateProgramParameters(CgVertexProgram);//プログラムのパラメータの更新
	

	gluSphere(quadric,1,60,60);
	//glutSolidCube(1);
	//Cgの無効化
	cgGLDisableTextureParameter(CgFs_CubeDecal);//無効化
	cgGLDisableProfile(CgVertexProfile);
	cgGLDisableProfile(CgFragmentProfile);

	drawXYZ();
	glutSwapBuffers();

	if(++angle >= 360)
	{
		angle = 0;
	}
}

void reshape(int w, int h)
{
	glViewport(0, 0, w, h);
	glMatrixMode(GL_PROJECTION);
	glLoadIdentity();
	gluPerspective(30.0, (double)w / (double)h, 1.0, 100.0);
	glMatrixMode(GL_MODELVIEW);
	glLoadIdentity();
}


void drawXYZ()
{
	glBegin(GL_LINES);

	glColor3f(1,0,0);
	glVertex3f(0,0,0);
	glVertex3f(200,0,0);

	glColor3f(0,1,0);
	glVertex3f(0,0,0);
	glVertex3f(0,200,0);

	glColor3f(0,0,1);
	glVertex3f(0,0,0);
	glVertex3f(0,0,200);

	glEnd();

	glColor3f(1,1,1);
}

目次

― その他 ―

Wiki内検索

計測中...(07.10.8〜)

Save The World






▲よろしければ広告のクリックもお願いします


▲ランキングに参加しました

管理人/副管理人のみ編集できます