Advertisement
r57shell

Dune2GroundEdit

Sep 17th, 2013
105
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. #include <windows.h>
  2. #include <GL/gl.h>
  3. #include <GL/glu.h>
  4. #include <stdio.h>
  5. #include <time.h>
  6.  
  7. #define GET_X_LPARAM(a) ((short)LOWORD(a))
  8. #define GET_Y_LPARAM(a) ((short)HIWORD(a))
  9.  
  10. unsigned short PlaneB[0x1000/2];
  11.  
  12. POINT camera = {0,0};
  13. POINT mouse;
  14. double zoom = 1;
  15. bool showgray = false;
  16. int state = 0;
  17.  
  18. struct Ground
  19. {
  20.     int width;
  21.     int height;
  22.     double *data;
  23.     Ground(int _width, int _height)
  24.     {
  25.         width = _width;
  26.         height = _height;
  27.         data = (double *)malloc(width*height*sizeof(double));
  28.         for (int x=0; x<width; ++x)
  29.             for (int y=0; y<height; ++y)
  30.                 (*this)[x][y] = 0;
  31.     }
  32.    
  33.     double *operator [](int x)
  34.     {
  35.         return data+x*height;
  36.     }
  37.    
  38.     ~Ground()
  39.     {
  40.         if (data)
  41.             free(data);
  42.     }
  43. };
  44.  
  45. struct DuneGround
  46. {
  47.     int width;
  48.     int height;
  49.     BYTE *data;
  50.     DuneGround(int _width, int _height)
  51.     {
  52.         width = _width;
  53.         height = _height;
  54.         data = (BYTE *)malloc(width*height*sizeof(BYTE));
  55.         for (int x=0; x<width; ++x)
  56.             for (int y=0; y<height; ++y)
  57.                 (*this)[x][y] = 0xB0;
  58.     }
  59.    
  60.     BYTE *operator [](int x)
  61.     {
  62.         return data+x*height;
  63.     }
  64.    
  65.     ~DuneGround()
  66.     {
  67.         if (data)
  68.             free(data);
  69.     }
  70.    
  71.     DuneGround(const DuneGround & g)
  72.     {
  73.         width = g.width;
  74.         height = g.height;
  75.         data = (BYTE *)malloc(width*height*sizeof(BYTE));
  76.         memcpy(data,g.data,width*height*sizeof(BYTE));
  77.     }
  78.    
  79.     const DuneGround & operator = (const DuneGround &g)
  80.     {
  81.         free(data);
  82.         width = g.width;
  83.         height = g.height;
  84.         data = (BYTE *)malloc(width*height*sizeof(BYTE));
  85.         memcpy(data,g.data,width*height*sizeof(BYTE));
  86.         return (*this);
  87.     }
  88. };
  89.  
  90. /*struct Point
  91. {
  92.     double x,y;
  93. }*/
  94.  
  95. DuneGround duneGround(64,64);
  96. DuneGround duneGroundNew(64,64);
  97.  
  98. Ground g(2*64+1,2*64+1);
  99. GLuint GroundTiles;
  100. GLuint GroundGrey;
  101.  
  102. // Declarations //////////////////////////////////////////////////////
  103.  
  104. GLuint LoadTextureRAW( const char * filename, int wrap );
  105. GLuint LoadVRAM( const char * vram, const char * pal);
  106. GLuint GenerateGround();
  107. void ChangeState(int _state);
  108. void RangeGround(double z);
  109. void LocalPick(int x, int y);
  110. void LoadMap( const char * filename );
  111. void SaveMap( const char * filename );
  112. void FreeTexture( GLuint texture );
  113.  
  114. LRESULT CALLBACK WndProc( HWND hWnd, UINT message,
  115.                           WPARAM wParam, LPARAM lParam );
  116.  
  117. VOID EnableOpenGL( HWND hWnd, HDC * hDC, HGLRC * hRC );
  118. VOID DisableOpenGL( HWND hWnd, HDC hDC, HGLRC hRC );
  119. void UpdateViewport(HWND hWnd);
  120. void Render(HWND hWnd, HDC hDC);
  121.  
  122.  
  123.  
  124. // WinMain ///////////////////////////////////////////////////////////
  125.  
  126. int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance,
  127.                     LPSTR lpCmdLine, int iCmdShow )
  128. {
  129.   WNDCLASS wc;
  130.   HWND hWnd;
  131.   HDC hDC;
  132.   HGLRC hRC;
  133.   MSG msg;
  134.   BOOL bQuit = FALSE;
  135.  
  136.   // register window class
  137.   wc.style = CS_OWNDC;
  138.   wc.lpfnWndProc = WndProc;
  139.   wc.cbClsExtra = 0;
  140.   wc.cbWndExtra = 0;
  141.   wc.hInstance = hInstance;
  142.   wc.hIcon = LoadIcon( NULL, IDI_APPLICATION );
  143.   wc.hCursor = LoadCursor( NULL, IDC_ARROW );
  144.   wc.hbrBackground = (HBRUSH)GetStockObject( BLACK_BRUSH );
  145.   wc.lpszMenuName = NULL;
  146.   wc.lpszClassName = "GLSample";
  147.   RegisterClass( &wc );
  148.  
  149.   // create main window
  150.   hWnd = CreateWindow(
  151.     "GLSample", "OpenGL Texture Sample",
  152.     WS_CAPTION | WS_POPUPWINDOW | WS_VISIBLE | WS_MAXIMIZEBOX | WS_THICKFRAME,
  153.     0, 0, 800, 600,
  154.     NULL, NULL, hInstance, NULL );
  155.  
  156.   // enable OpenGL for the window
  157.   EnableOpenGL( hWnd, &hDC, &hRC );
  158.   UpdateViewport( hWnd);
  159.  
  160.   // load our texture
  161.   GroundTiles = LoadTextureRAW( "tex1.bmp", TRUE );
  162.   //LoadMap("map_18.bin");
  163.  
  164.   srand(time(0));
  165.   GroundGrey = GenerateGround();
  166.   //texture = LoadVRAM( "vram.bin", "pal.bin" );
  167.  
  168.   int startTime = GetTickCount();
  169.   int prevTime = startTime;
  170.  
  171.   // program main loop
  172.   while ( !bQuit ) {
  173.  
  174.     // check for messages
  175.     if ( PeekMessage( &msg, NULL, 0, 0, PM_REMOVE ) ) {
  176.  
  177.       // handle or dispatch messages
  178.       if ( msg.message == WM_QUIT ) {
  179.         bQuit = TRUE;
  180.       } else {
  181.         TranslateMessage( &msg );
  182.         DispatchMessage( &msg );
  183.       }
  184.  
  185.     } else {
  186.         int n = GetTickCount();
  187.         if (n - prevTime > 1000/40)
  188.         {
  189.             Render(hWnd, hDC);
  190.             prevTime = n;
  191.         }
  192.         else
  193.             Sleep(1);
  194.     }
  195.  
  196.   }
  197.  
  198.   // free the texture
  199.   FreeTexture( GroundTiles );
  200.   FreeTexture( GroundGrey );
  201.  
  202.   // shutdown OpenGL
  203.   DisableOpenGL( hWnd, hDC, hRC );
  204.  
  205.   // destroy the window explicitly
  206.   DestroyWindow( hWnd );
  207.  
  208.   return msg.wParam;
  209.  
  210. }
  211.  
  212. void Render(HWND hWnd, HDC hDC)
  213. {
  214.     // OpenGL animation code goes here
  215.     RECT rc;
  216.     GetClientRect(hWnd,&rc);
  217.     double cx = int((camera.x+mouse.x-(rc.right/2))/32.0/zoom);
  218.     double cy = int((camera.y+mouse.y-(rc.bottom/2))/32.0/zoom);
  219.     if (state == 1
  220.      && (int)(cx*2) <64*2+1 && (int)(cx*2)>=0
  221.      && (int)(cy*2) <64*2+1 && (int)(cy*2)>=0)
  222.         LocalPick(cx*2,cy*2);//RangeGround(g[(int)(cx*2)][(int)(cy*2)]);*/
  223.  
  224.     glClearColor( 0.0f, 0.0f, 0.0f, 0.0f );
  225.     glClear( GL_COLOR_BUFFER_BIT );
  226.  
  227.     // setup texture mapping
  228.     glEnable( GL_TEXTURE_2D );
  229.     glBindTexture( GL_TEXTURE_2D, GroundTiles );
  230.  
  231.     glPushMatrix();
  232.     glBegin( GL_QUADS );
  233.  
  234.     // tiles
  235.     /*double tw = 1.0/64;
  236.     for (int i=0; i<32; ++i)
  237.     {
  238.         for (int j=0; j<64; ++j)
  239.         {
  240.             int id = PlaneB[i*64+j]&0x7FF;
  241.             int idx = id&63;
  242.             int idy = id>>6;
  243.             glTexCoord2d(tw*(idx+0),tw*(idy+0)); glVertex2d(-1.0+tw*j,+1.0-tw*i);
  244.             glTexCoord2d(tw*(idx+1),tw*(idy+0)); glVertex2d(-1.0+tw*(j+1),+1.0-tw*i);
  245.             glTexCoord2d(tw*(idx+1),tw*(idy+1)); glVertex2d(-1.0+tw*(j+1),+1.0-tw*(i+1));
  246.             glTexCoord2d(tw*(idx+0),tw*(idy+1)); glVertex2d(-1.0+tw*j,+1.0-tw*(i+1));
  247.         }
  248.     }
  249.     glTexCoord2d(0.0,0.0); glVertex2d(-8.0,+8.0);
  250.     glTexCoord2d(1.0,0.0); glVertex2d(+8.0,+8.0);
  251.     glTexCoord2d(1.0,1.0); glVertex2d(+8.0,-8.0);
  252.     glTexCoord2d(0.0,1.0); glVertex2d(-8.0,-8.0);*/
  253.     GetClientRect(hWnd, &rc);
  254.     double tw = 1.0/16;
  255.     for (int i=0; i<64; ++i)
  256.     {
  257.         for (int j=0; j<64; ++j)
  258.         {
  259.             int id;
  260.             if (state == 1)
  261.                 id = duneGroundNew[j][i];
  262.             else
  263.                 id = duneGround[j][i];
  264.             int idx = id&15;
  265.             int idy = (id>>4);
  266.             glTexCoord2d(tw*(idx+0),1-tw*(idy+0)); glVertex2d(j,-i);
  267.             glTexCoord2d(tw*(idx+1),1-tw*(idy+0)); glVertex2d(j+1,-i);
  268.             glTexCoord2d(tw*(idx+1),1-tw*(idy+1)); glVertex2d(j+1,-(i+1));
  269.             glTexCoord2d(tw*(idx+0),1-tw*(idy+1)); glVertex2d(j,-(i+1));
  270.            
  271.         }
  272.     }
  273.     glEnd();
  274.  
  275.     if (showgray)
  276.     {
  277.     glBindTexture( GL_TEXTURE_2D, GroundGrey );
  278.     glBegin( GL_QUADS );
  279.           glTexCoord2d(0,0); glVertex2d(0,-0);
  280.           glTexCoord2d(1,0); glVertex2d(64,-0);
  281.           glTexCoord2d(1,1); glVertex2d(64,-64);
  282.           glTexCoord2d(0,1); glVertex2d(0,-64);
  283.     glEnd();
  284.     }
  285.  
  286.     /*glBindTexture( GL_TEXTURE_2D, texture );
  287.     glBegin( GL_QUADS );
  288.        
  289.         glTexCoord2d(tw*(3+0),1-tw*(0+0)); glVertex2d(cx,-cy);
  290.         glTexCoord2d(tw*(3+1),1-tw*(0+0)); glVertex2d(cx+1,-cy);
  291.         glTexCoord2d(tw*(3+1),1-tw*(0+1)); glVertex2d(cx+1,-cy-1);
  292.         glTexCoord2d(tw*(3+0),1-tw*(0+1)); glVertex2d(cx,-cy-1);
  293.     glEnd();*/
  294.     glPopMatrix();
  295.  
  296.     SwapBuffers( hDC );
  297. }
  298.  
  299.  
  300. // Texture ///////////////////////////////////////////////////////////
  301.  
  302. // load a 256x256 RGB .RAW file as a texture
  303. GLuint LoadTextureRAW( const char * filename, int wrap )
  304. {
  305.   GLuint texture;
  306.   int width, height;
  307.   BYTE * data;
  308.   FILE * file;
  309.   FILE *f;
  310.   BYTE tmp;
  311.   int i;
  312.  
  313.   // open texture data
  314.   file = fopen( filename, "rb" );
  315.   if ( file == NULL ) return 0;
  316.  
  317.   // allocate buffer
  318.   width = 512;
  319.   height = 512;
  320.   data = (BYTE*)malloc( width * height * 3 );
  321.  
  322.   // read texture data
  323.  
  324.   fseek( file, 0x36, SEEK_SET);
  325.   fread( data, width * height * 3, 1, file );
  326.   fclose( file );
  327.  
  328.   for (i=0; i<width*height; ++i)
  329.   {
  330.         tmp = data[i*3];
  331.         data[i*3] = data[i*3+2];
  332.         data[i*3+2] = tmp;
  333.   }
  334.  
  335.   // allocate a texture name
  336.   glGenTextures( 1, &texture );
  337.  
  338.   // select our current texture
  339.   glBindTexture( GL_TEXTURE_2D, texture );
  340.  
  341.   // select modulate to mix texture with color for shading
  342.   glTexEnvf( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE );
  343.  
  344.   // when texture area is small, bilinear filter the closest MIP map
  345.   glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST );
  346.  
  347.   // when texture area is large, bilinear filter the first MIP map
  348.   glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
  349.  
  350.   // if wrap is true, the texture wraps over at the edges (repeat)
  351.   //       ... false, the texture ends at the edges (clamp)
  352.   glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S,
  353.                    wrap ? GL_REPEAT : GL_CLAMP );
  354.   glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T,
  355.                    wrap ? GL_REPEAT : GL_CLAMP );
  356.  
  357.   // build our texture MIP maps
  358.   //gluBuild2DMipmaps( GL_TEXTURE_2D, 3, width,
  359.   //  height, GL_RGB, GL_UNSIGNED_BYTE, data );
  360.   glTexImage2D( GL_TEXTURE_2D, 0, GL_RGB, width,
  361.     height, 0, GL_RGB, GL_UNSIGNED_BYTE, data );
  362.  
  363.   // free buffer
  364.   free( data );
  365.  
  366.   return texture;
  367.  
  368. }
  369.  
  370. double randf()
  371. {
  372.     return rand()/double(RAND_MAX);
  373. }
  374.  
  375. void GenerateGroundRecursive(Ground &g, int x, int y, int width, int height)
  376. {
  377.     if (width <= 1 || height <= 1)
  378.         return;
  379.     double a,b,c,d;
  380.     a = g[x      ][y      ];
  381.     b = g[x+width][y      ];
  382.     c = g[x      ][y+height];
  383.     d = g[x+width][y+height];
  384.  
  385.     g[(x + (x + width))/2][ y                  ] = (a + b)/2;
  386.     g[ x                 ][(y + (y + height))/2] = (a + c)/2;
  387.     g[(x + (x + width))/2][ y + height         ] = (c + d)/2;
  388.     g[ x + width         ][(y + (y + height))/2] = (b + d)/2;
  389.    
  390.     double z = (a+b+c+d)/4+((-1+randf()*2)*width/64/2);
  391.     if (z > 1)
  392.         z = 1;
  393.     if (z < 0)
  394.         z = 0;
  395.     g[(x + (x + width))/2][(y + (y + height))/2] = z;
  396.    
  397.     GenerateGroundRecursive(g, x          , y           , width/2, height/2);
  398.     GenerateGroundRecursive(g, x + width/2, y           , width/2, height/2);
  399.     GenerateGroundRecursive(g, x          , y + height/2, width/2, height/2);
  400.     GenerateGroundRecursive(g, x + width/2, y + height/2, width/2, height/2);
  401. }
  402.  
  403. void LocalPick(int x, int y)
  404. {
  405.     static bool was[2*64+1][2*64+1];
  406.  
  407.     for (int i=0; i<2*64+1; ++i)
  408.         for (int j=0; j<2*64+1; ++j)
  409.             was[i][j] = false;
  410.  
  411.     static int X[(2*64+1)*(2*64+1)];
  412.     static int Y[(2*64+1)*(2*64+1)];
  413.     double z = g[x][y];
  414.     int s = 0,e = 0;
  415.     X[e] = x;
  416.     Y[e] = y;
  417.     was[x][y] = true;
  418.     ++e;
  419.     while (s < e)
  420.     {
  421.         for (int i=-1; i<2; ++i)
  422.             for (int j=-1; j<2; ++j)
  423.                 if (X[s]+i>=0 && X[s]+i<2*64+1
  424.                  && Y[s]+j>=0 && Y[s]+j<2*64+1
  425.                  && !was[X[s]+i][Y[s]+j]
  426.                  && g[X[s]+i][Y[s]+j]>=z)
  427.                 {
  428.                     X[e] = X[s]+i;
  429.                     Y[e] = Y[s]+j;
  430.                     was[X[e]][Y[e]] = true;
  431.                     ++e;
  432.                 }
  433.         ++s;
  434.     }
  435.    
  436.     for (int x=0; x<64; ++x)
  437.     {
  438.         for (int y=0; y<64; ++y)
  439.         {
  440.             int mask = 0;
  441.             for (int i=0; i<3; ++i)
  442.                 for (int j=0; j<3; ++j)
  443.                     if (was[i+x*2][j+y*2])
  444.                         mask |= 1<<(i+j*3);
  445.  
  446.             int k = 0;
  447.             //1    2   4
  448.             //8   16  32
  449.             //64 128 256
  450.             if ( (mask&(1+2+4)) == (1+2+4))
  451.                 k++;
  452.             if ( (mask&(4+32+256)) == (4+32+256))
  453.                 k |= 2;
  454.             if ( (mask&(64+128+256)) == (64+128+256))
  455.                 k |= 4;
  456.             if ( (mask&(1+8+64)) == (1+8+64))
  457.                 k |= 8;
  458.             int id = 0x80+k;
  459.             if ( k == 0)
  460.                 id = duneGround[x][y];
  461.             if ( k == 0 && (mask & 16))
  462.                 id = 0x80;
  463.             if ( k == 3 && !(mask & 16))
  464.                 id = 0x3C;
  465.             if ( k == 6 && !(mask & 16))
  466.                 id = 0x3D;
  467.             if ( k == 12 && !(mask & 16))
  468.                 id = 0x3F;
  469.             if ( k == 9 && !(mask & 16))
  470.                 id = 0x3E;
  471.  
  472.             duneGroundNew[x][y] = id;
  473.         }
  474.     }
  475. }
  476.  
  477. void RangeGround(double z)
  478. {
  479.     for (int x=0; x<64; ++x)
  480.     {
  481.         for (int y=0; y<64; ++y)
  482.         {
  483.             int mask = 0;
  484.             for (int i=0; i<3; ++i)
  485.                 for (int j=0; j<3; ++j)
  486.                     if (g[i+x*2][j+y*2]>z)
  487.                         mask |= 1<<(i+j*3);
  488.             int k = 0;
  489.             //1    2   4
  490.             //8   16  32
  491.             //64 128 256
  492.             if ( (mask&(1+2+4)) == (1+2+4))
  493.                 k++;
  494.             if ( (mask&(4+32+256)) == (4+32+256))
  495.                 k |= 2;
  496.             if ( (mask&(64+128+256)) == (64+128+256))
  497.                 k |= 4;
  498.             if ( (mask&(1+8+64)) == (1+8+64))
  499.                 k |= 8;
  500.             int id = 0x80+k;
  501.             if ( k == 0)
  502.                 id = 0xB0;
  503.             if ( k == 0 && (mask & 16))
  504.                 id = 0x80;
  505.             if ( k == 3 && !(mask & 16))
  506.                 id = 0x3C;
  507.             if ( k == 6 && !(mask & 16))
  508.                 id = 0x3D;
  509.             if ( k == 12 && !(mask & 16))
  510.                 id = 0x3F;
  511.             if ( k == 9 && !(mask & 16))
  512.                 id = 0x3E;
  513.  
  514.             duneGround[x][y] = id;
  515.         }
  516.     }
  517. }
  518.  
  519. GLuint GenerateGround()
  520. {
  521.     g[        0][         0] = randf();
  522.     g[g.width-1][         0] = randf();
  523.     g[        0][g.height-1] = randf();
  524.     g[g.width-1][g.height-1] = randf();
  525.  
  526.     GenerateGroundRecursive(g, 0, 0, g.width-1, g.height-1);
  527.    
  528.     BYTE *data = (BYTE*)malloc( (g.width-1) * (g.height-1) * 3 );
  529.  
  530.     for (int x=0; x<g.width-1; ++x)
  531.     {
  532.         for (int y=0; y<g.height-1; ++y)
  533.         {
  534.             for (int i=0; i<3; ++i)
  535.                 data[(x + y*(g.width-1))*3 + i] = g[x][y]*255;
  536.         }
  537.     }
  538.    
  539.     GLuint texture;
  540.     glGenTextures( 1, &texture );
  541.  
  542.     glBindTexture( GL_TEXTURE_2D, texture );
  543.    
  544.     glTexEnvf( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE );
  545.  
  546.     // when texture area is small, bilinear filter the closest MIP map
  547.     glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST );
  548.    
  549.     // when texture area is large, bilinear filter the first MIP map
  550.     glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
  551.  
  552.     // if wrap is true, the texture wraps over at the edges (repeat)
  553.     //       ... false, the texture ends at the edges (clamp)
  554.     glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP );
  555.     glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP );
  556.                  
  557.     glTexImage2D( GL_TEXTURE_2D, 0, GL_RGB, g.width-1, g.height-1, 0, GL_RGB, GL_UNSIGNED_BYTE, data );
  558.  
  559.     free(data);
  560.  
  561.    
  562.     /*for (int x=0; x<64; ++x)
  563.     {
  564.         for (int y=0; y<64; ++y)
  565.         {
  566.             int t;
  567.             if (g[x*2][y*2]>0.5)
  568.                 t = 0x8F;
  569.             else
  570.                 t = 0xB0;
  571.             Map[x+y*64]=t;
  572.         }
  573.     }
  574.    
  575.     for (int x=0; x<64; ++x)
  576.     {
  577.         for (int y=0; y<64; ++y)
  578.         {
  579.             int t;
  580.             if (g[x*2][y*2]>0.5)
  581.                 t = 0x8F;
  582.             else
  583.                 t = 0xB0;
  584.             Map[x+y*64]=t;
  585.         }
  586.     }
  587.     for (int x=0; x<64; ++x)
  588.     {
  589.         for (int y=0; y<64; ++y)
  590.         {
  591.             int k = 0;
  592.             if ( y > 0  && Map[x+(y-1)*64] == 0x8F)
  593.                 k++;
  594.             if ( x < 63 && Map[x+1+y*64] == 0x8F)
  595.                 k |= 2;
  596.             if ( y < 63 && Map[x+(y+1)*64] == 0x8F)
  597.                 k |= 4;
  598.             if ( x > 0 && Map[x-1+y*64] == 0x8F)
  599.                 k |= 8;
  600.             if (k != 0 && Map[x+y*64] != 0x8F)
  601.                 Map[x+y*64] = 0x80 + k;
  602.         }
  603.     }*/
  604.     return texture;
  605. }
  606.  
  607. // load a 256x256 RGB .RAW file as a texture
  608. GLuint LoadVRAM( const char * vram, const char * pal)
  609. {
  610.     GLuint texture;
  611.     int width, height;
  612.     BYTE palette[16*4][3];
  613.     BYTE * data;
  614.     BYTE * vdata;
  615.     FILE * file;
  616.     FILE *f;
  617.     int x;
  618.     int y;
  619.  
  620.     file = fopen( pal, "rb" );
  621.     if ( file == NULL ) return 0;
  622.  
  623.     for (int i=0; i<16*4; ++i)
  624.     {
  625.         BYTE tmp = 0;
  626.         short color;
  627.         fread(&tmp, 1, 1, file);
  628.         color = tmp << 8;
  629.         fread(&tmp, 1, 1, file);
  630.         color |= tmp;
  631.    
  632.         for (int j=0; j<3; ++j)
  633.         {
  634.             palette[i][j] = (((color >> (j*4))&0xE)/double(0xE))*0xFF;
  635.         }
  636.     }
  637.     fclose( file );
  638.      
  639.     // open texture data
  640.     file = fopen( vram, "rb" );
  641.     if ( file == NULL ) return 0;
  642.  
  643.     // allocate buffer
  644.     width = 512;
  645.     height = 512;
  646.     data = (BYTE*)malloc( width * height * 3 );
  647.     vdata = (BYTE*)malloc( 0x800 * 32 );
  648.  
  649.     // read texture data
  650.  
  651.     fread( vdata,  0x800 * 32, 1, file );
  652.     fclose( file );
  653.  
  654.     x = 0;
  655.     y = 0;
  656.     for (int i=0; i < 0x800; ++i)
  657.     {
  658.         for (int v = 0; v < 8; ++v)
  659.             for (int u = 0; u < 4; ++u)
  660.             {
  661.                 BYTE tmp = vdata[i*32+v*4+u];
  662.                 BYTE *ptr = data+((y+v)*512+x+u*2)*3;
  663.                 for (int j=0; j<3; ++j)
  664.                 {
  665.                     ptr[j] = palette[tmp>>4][j];
  666.                     ptr[j+3] = palette[tmp&0xF][j];
  667.                 }
  668.                 /*for (int j=0; j<3; ++j)
  669.                 {
  670.                     ptr[j] = palette[i%17][j];
  671.                     ptr[j+3] = palette[i%17][j];
  672.                 }*/
  673.             }
  674.         x += 8;
  675.         if (x == 512)
  676.         {
  677.             x = 0;
  678.             y += 8;
  679.         }
  680.     }
  681.  
  682.     for (int i=0; i<0x1000/2; ++i)
  683.     {
  684.         PlaneB[i]=(vdata[0xC000+i*2]<<8)|vdata[0xC000+i*2+1];
  685.     }
  686.  
  687.   // allocate a texture name
  688.   glGenTextures( 1, &texture );
  689.  
  690.   // select our current texture
  691.   glBindTexture( GL_TEXTURE_2D, texture );
  692.  
  693.   // select modulate to mix texture with color for shading
  694.   glTexEnvf( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE );
  695.  
  696.   // when texture area is small, bilinear filter the closest MIP map
  697.   glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST );
  698.   // when texture area is large, bilinear filter the first MIP map
  699.   glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST );
  700.  
  701.   // if wrap is true, the texture wraps over at the edges (repeat)
  702.   //       ... false, the texture ends at the edges (clamp)
  703.   glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
  704.   glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
  705.  
  706.   // build our texture MIP maps
  707.   gluBuild2DMipmaps( GL_TEXTURE_2D, 3, width,
  708.     height, GL_RGB, GL_UNSIGNED_BYTE, data );
  709.  
  710.   // free buffer
  711.   free( data );
  712.  
  713.   // free vram data
  714.   free ( vdata );
  715.  
  716.   return texture;
  717.  
  718. }
  719.  
  720. void LoadMap( const char * filename )
  721. {
  722.     FILE *f = fopen(filename, "rb");
  723.     if (!f)
  724.         return;
  725.     BYTE tmp;
  726.     for (int y=0; y<64; ++y)
  727.         for (int x=0; x<64; ++x)
  728.         {
  729.             fread(&tmp,1,1,f);
  730.             duneGround[x][y]=tmp;
  731.         }
  732.     fclose(f);
  733. }
  734.  
  735. void SaveMap( const char * filename )
  736. {
  737.     FILE *f = fopen(filename,"wb");
  738.     if (!f)
  739.         return;
  740.     for (int y=0; y<64; ++y)
  741.         for (int x=0; x<64; ++x)
  742.             fwrite(&duneGround[x][y],1,1,f);
  743.     fclose(f);
  744. }
  745.  
  746. void FreeTexture( GLuint texture )
  747. {
  748.     glDeleteTextures( 1, &texture );
  749. }
  750.  
  751. bool mousedown = false;
  752.  
  753. void UpdateViewport(HWND hWnd)
  754. {
  755.     RECT rc;
  756.     GetClientRect(hWnd, &rc);
  757.     glViewport( 0, 0, rc.right, rc.bottom);
  758.     glMatrixMode( GL_PROJECTION );
  759.     glLoadIdentity();
  760.     //gluOrtho2D( 0,0,500,500);//camera.x, camera.y, camera.x+rc.right, camera.y+rc.bottom);
  761.     double scale = 1/32.0/zoom;
  762.     glScalef(64.0/rc.right*zoom,64.0/rc.bottom*zoom,1);
  763.     glTranslatef( -camera.x*scale, camera.y*scale, 0);
  764.     glMatrixMode( GL_MODELVIEW );
  765. }
  766.  
  767. void ChangeState(int _state)
  768. {
  769.     state = _state;
  770.     if (state == 1)
  771.         duneGroundNew = duneGround;
  772. }
  773.  
  774. // Window Proc ///////////////////////////////////////////////////////
  775.  
  776. LRESULT CALLBACK WndProc( HWND hWnd, UINT message,
  777.                           WPARAM wParam, LPARAM lParam )
  778. {
  779.     switch ( message ) {
  780.  
  781.     case WM_CREATE:
  782.         return 0;
  783.  
  784.     case WM_CLOSE:
  785.         PostQuitMessage( 0 );
  786.         return 0;
  787.  
  788.     case WM_SIZE:
  789.         UpdateViewport(hWnd);
  790.         break;
  791.  
  792.     case WM_DESTROY:
  793.         return 0;
  794.  
  795.     case WM_KEYDOWN:
  796.     switch ( wParam ) {
  797.  
  798.     case VK_ESCAPE:
  799.         PostQuitMessage( 0 );
  800.         return 0;
  801.  
  802.     case 'S':
  803.         SaveMap("map.bin");
  804.         return 0;
  805.  
  806.     case 'R':
  807.         FreeTexture(GroundGrey);
  808.         GroundGrey = GenerateGround();
  809.         return 0;
  810.     case 'E':
  811.         ChangeState(state^1);
  812.         return 0;
  813.      
  814.     case VK_SPACE:
  815.         showgray = !showgray;
  816.         return 0;
  817.     }
  818.     return 0;
  819.  
  820.   case WM_MOUSEWHEEL:
  821.     {
  822.     RECT rc;
  823.     GetClientRect(hWnd,&rc);
  824.     mouse.x = GET_X_LPARAM(lParam);
  825.     mouse.y = GET_Y_LPARAM(lParam);
  826.     short zDelta = HIWORD(wParam);
  827.     if (zDelta > 0)
  828.     {
  829.         zoom *= 1.2;
  830.         camera.x *= 1.2;//(camera.x + mouse.x) * (zoom/(zoom-0.1)) - mouse.x;
  831.         camera.y *= 1.2;//(camera.y + mouse.y) * (zoom/(zoom-0.1)) - mouse.y;
  832.     }
  833.     else
  834.     {
  835.         zoom /= 1.2;
  836.         camera.x /= 1.2;
  837.         camera.y /= 1.2;
  838.     }
  839.    
  840.     UpdateViewport(hWnd);
  841.     }
  842.     break;
  843.   case WM_LBUTTONDOWN:
  844.     {
  845.     SetCapture(hWnd);
  846.     mouse.x = GET_X_LPARAM(lParam);
  847.     mouse.y = GET_Y_LPARAM(lParam);
  848.     RECT rc;
  849.     GetClientRect(hWnd,&rc);
  850.     int cx = int((camera.x+mouse.x-(rc.right/2))/32.0/zoom);
  851.     int cy = int((camera.y+mouse.y-(rc.bottom/2))/32.0/zoom);
  852.     if (state == 1)
  853.         duneGround = duneGroundNew;
  854.     mousedown = true;
  855.     }
  856.     break;
  857.   case WM_MOUSEMOVE:
  858.     if (mousedown)
  859.     {
  860.         int xPos = mouse.x; mouse.x = GET_X_LPARAM(lParam);
  861.         int yPos = mouse.y; mouse.y = GET_Y_LPARAM(lParam);
  862.         camera.x -= mouse.x-xPos;
  863.         camera.y -= mouse.y-yPos;
  864.         UpdateViewport(hWnd);
  865.     }
  866.     mouse.x = GET_X_LPARAM(lParam);
  867.     mouse.y = GET_Y_LPARAM(lParam);
  868.     break;
  869.   case WM_LBUTTONUP:
  870.     ReleaseCapture();
  871.     mousedown = false;
  872.     break;
  873.   }
  874.   return DefWindowProc( hWnd, message, wParam, lParam );
  875. }
  876.  
  877.  
  878. // OpenGL ////////////////////////////////////////////////////////////
  879.  
  880. // Enable OpenGL
  881.  
  882. VOID EnableOpenGL( HWND hWnd, HDC * hDC, HGLRC * hRC )
  883. {
  884.   PIXELFORMATDESCRIPTOR pfd;
  885.   int iFormat;
  886.  
  887.   // get the device context (DC)
  888.   *hDC = GetDC( hWnd );
  889.  
  890.   // set the pixel format for the DC
  891.   ZeroMemory( &pfd, sizeof( pfd ) );
  892.   pfd.nSize = sizeof( pfd );
  893.   pfd.nVersion = 1;
  894.   pfd.dwFlags = PFD_DRAW_TO_WINDOW |
  895.     PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER;
  896.   pfd.iPixelType = PFD_TYPE_RGBA;
  897.   pfd.cColorBits = 24;
  898.   pfd.cDepthBits = 16;
  899.   pfd.iLayerType = PFD_MAIN_PLANE;
  900.   iFormat = ChoosePixelFormat( *hDC, &pfd );
  901.   SetPixelFormat( *hDC, iFormat, &pfd );
  902.  
  903.   // create and enable the render context (RC)
  904.   *hRC = wglCreateContext( *hDC );
  905.   wglMakeCurrent( *hDC, *hRC );
  906.  
  907. }
  908.  
  909. // Disable OpenGL
  910.  
  911. VOID DisableOpenGL( HWND hWnd, HDC hDC, HGLRC hRC )
  912. {
  913.   wglMakeCurrent( NULL, NULL );
  914.   wglDeleteContext( hRC );
  915.   ReleaseDC( hWnd, hDC );
  916. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement