2015年11月29日日曜日

OpenGL:テキスチャーとライト

四角形にテキスチャーをはって、
スポットライトをぐるぐるしてみる。
読み込みファイルは、24ビット ビットマップファイルを読み込み。

今回実行時読み込んだファイル
実行結果



#include <windows.h>
#include <GL/gl.h>
#include <GL/glu.h>
#include <math.h>
#define M_PI 3.141592653589793
#include "GL/glut.h"

BITMAPFILEHEADER bmpFH;
BITMAPINFOHEADER bmpIH;
static GLubyte *imageBuf;
static GLuint texName;

//24色 bmpファイルの読み込み
void readFile(PSTR fName){
  HANDLE hFile;
  DWORD readBytes;
  /* ファイルのオープン*/
  hFile = CreateFile(fName , GENERIC_READ , 0 , NULL ,
OPEN_EXISTING , FILE_ATTRIBUTE_NORMAL , NULL);
  /* ヘッダ部分の読み込み */
  ReadFile(hFile,&bmpFH,sizeof(BITMAPFILEHEADER),&readBytes,NULL);

  ReadFile(hFile , &bmpIH , sizeof (BITMAPINFOHEADER) , &readBytes , NULL);

  /*サイズ分のバッファ確保 */
  imageBuf = (GLubyte*)malloc(bmpIH.biSizeImage*sizeof(GLubyte));
  /*ファイル読み込み*/
  ReadFile(hFile , imageBuf,bmpIH.biSizeImage*sizeof(GLubyte),&readBytes,NULL);
  /*ファイルを閉じる*/
  CloseHandle(hFile);

}

void display(void)
{
  GLdouble len = 1000;
  GLdouble len2 = 0.9;
  GLdouble xPos,yPos,xCPos,yCPos;
  int ii,jj;
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  glColor3d(1,1,1);

  glBegin(GL_LINES);
  glVertex3d(-len,0,0);
  glVertex3d(len,0,0);
  glVertex3d(0,-len,0);
  glVertex3d(0,len,0);
  glVertex3d(0,0,-len);
  glVertex3d(0,0,len);
  glEnd();

  GLdouble nv[] = {0,0,1};
  glEnable(GL_TEXTURE_2D);
  glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
  glBindTexture(GL_TEXTURE_2D,texName);

  glBegin(GL_QUADS);

  double num = 450;

  for(ii = 0;ii<=num;ii++){
  for(jj = 0;jj<=num;jj++){

   xPos = jj/num;
   yPos = ii/num;

 xCPos = jj/num;
 yCPos = ii/num;

   glNormal3dv(nv);
   glTexCoord2d(xPos,yPos);glVertex3d(xPos,yPos,0);
   glNormal3dv(nv);
   glTexCoord2d(xPos+0.01,yPos);glVertex3d(xPos+0.01,yPos,0);
   glNormal3dv(nv);
   glTexCoord2d(xPos+0.01,yPos+0.01);glVertex3d(xPos+0.01,yPos+0.01,0);
   glNormal3dv(nv);
   glTexCoord2d(xPos,yPos+0.01);glVertex3d(xPos,yPos+0.01,0);
  }
  }

  glDisable(GL_TEXTURE_2D);

  glEnd();
  glFlush();
  glutSwapBuffers();
}
void myReshape(GLsizei w, GLsizei h){
  glViewport(0, 0, w, h);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  glOrtho(0, 1, 0, 1, -1, 1);
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
}


void idleFunc(void){
  static GLdouble x = 0;
  static GLdouble y = 0;
  static GLint theta = 0;
  static GLfloat spot_direction[] = { 0.0, 0.05, -1.0 } ;

  static GLdouble agree;

  theta +=5;

  if(theta >= 360){
theta = 0;
  }
  // スポットライトの方向指定
  agree = M_PI/180*theta;
  x = cos(agree)/4+0.25;
  y = sin(agree)/4+0.25;
  spot_direction[0] = x;
  spot_direction[1] = y;

  glLightfv(GL_LIGHT0, GL_SPOT_DIRECTION, spot_direction);
  glutPostRedisplay();
  Sleep(1);
  glutIdleFunc(idleFunc);

}

void myinit (char* argv)
{
  GLfloat mat_specular[] = { 1.0, 1.0, 1.0, 1.0 };
  GLfloat mat_shininess[] = { 0.0 };
  GLfloat light_position[] = {0.0, 0.0, 1.5, 1.0 };
  GLfloat spot_direction[] = { 0.0, 0.05, -1.0 };
  GLfloat light_specular[] = { 1.0, 1.0, 1.0, 1.0 };

  GLfloat lightBlack[] = {0.0,0.0,0.0,0.0};

  // ライトの設定
  glClearColor (0.0, 0.0, 0.0, 0.0);
  glShadeModel (GL_SMOOTH);

  glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular);
  glMaterialfv(GL_FRONT, GL_SHININESS, mat_shininess);

  glLightfv(GL_LIGHT0, GL_POSITION, light_position);
  glLightfv(GL_LIGHT0, GL_AMBIENT,  lightBlack);
  glLightfv(GL_LIGHT0, GL_DIFFUSE,  lightBlack);

  glLightfv(GL_LIGHT0, GL_SPOT_DIRECTION, spot_direction);
  glLightfv(GL_LIGHT0, GL_SPECULAR, light_specular);
  glLightf (GL_LIGHT0, GL_SPOT_CUTOFF, 5.0);

  glClearColor (0.0, 0.0, 0.0, 0.0);

  readFile(argv);

  //Textureの設定
  glGenTextures(1,&texName);
  glBindTexture(GL_TEXTURE_2D,texName);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER,
 GL_NEAREST);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
 GL_NEAREST);

  glTexImage2D(GL_TEXTURE_2D,0,3,bmpIH.biWidth,bmpIH.biHeight,0
  ,GL_BGR_EXT,GL_UNSIGNED_BYTE,imageBuf);

  glEnable(GL_DEPTH_TEST);
  glEnable(GL_LIGHTING);
  glEnable(GL_LIGHT0);
}



int main(int argc, char** argv)
{
  glutInit(&argc, argv);
  glutInitDisplayMode (GLUT_DOUBLE | GLUT_RGBA);
  glutCreateWindow(argv[0]);
  glutPositionWindow(100,100);
  glutReshapeFunc (myReshape);
  glutDisplayFunc(display);
  myinit (argv[1]);
  glutIdleFunc(idleFunc);
  glutMainLoop();
}

0 件のコメント:

コメントを投稿