Author Topic: OpenGL Example Full Screen  (Read 5337 times)

0 Members and 1 Guest are viewing this topic.

Offline rain_storm

  • Here comes the Rain
  • DBF Aficionado
  • ******
  • Posts: 3084
  • Karma: 182
  • Rain never hurt nobody
    • View Profile
    • org_100h
OpenGL Example Full Screen
« on: April 03, 2008 »
This is the openGL example that comes with FASM but I changed it so that it ran in full screen instead of a window. Hope someone finds this useful

Code: [Select]
; OpenGL programming example
format PE GUI 4.0
entry start
include 'win32a.inc'
include 'opengl.inc'

RESX = 640
RESY = 480
FULLSCREEN = WS_VISIBLE+WS_MAXIMIZE+WS_POPUP
WINDOW = WS_VISIBLE+WS_OVERLAPPEDWINDOW+WS_CLIPCHILDREN+WS_CLIPSIBLINGS




section '.data' data readable writeable
  _title db 'OPENGL FULLSCREEN',0
  _class db 'OPENGL',0
  wc WNDCLASS 0,WindowProc,0,0,NULL,NULL,NULL,NULL,NULL,_class
  hwnd dd ?
  hdc dd ?
  hrc dd ?
  msg MSG
  rc RECT
  pfd PIXELFORMATDESCRIPTOR
  active dd ?




section '.code' code readable executable

  start:
invoke GetModuleHandle,0
mov [wc.hInstance],eax
invoke LoadIcon,0,IDI_APPLICATION
mov [wc.hIcon],eax
invoke LoadCursor,0,IDC_ARROW
mov [wc.hCursor],eax
invoke RegisterClass,wc
;invoke  CreateWindowEx,0,_class,_title,WINDOW,32,32,RESX,RESY,NULL,NULL,[wc.hInstance],NULL
invoke CreateWindowEx,NULL,_class,_title,FULLSCREEN,32,32,RESX,RESY,NULL,NULL,[wc.hInstance],NULL
mov [hwnd],eax

  msg_loop:
invoke InvalidateRect,[hwnd],NULL,FALSE
invoke GetMessage,msg,NULL,0,0
or eax,eax
jz end_loop
invoke TranslateMessage,msg
invoke DispatchMessage,msg
jmp msg_loop

  end_loop:
invoke ExitProcess,[msg.wParam]

proc WindowProc hwnd,wmsg,wparam,lparam
push ebx esi edi
cmp [wmsg],WM_CREATE
je .wmcreate
cmp [wmsg],WM_SIZE
je .wmsize
cmp [wmsg],WM_ACTIVATEAPP
je .wmactivateapp
cmp [wmsg],WM_PAINT
je .wmpaint
cmp [wmsg],WM_KEYDOWN
je .wmkeydown
cmp [wmsg],WM_DESTROY
je .wmdestroy

  .defwndproc:
invoke DefWindowProc,[hwnd],[wmsg],[wparam],[lparam]
jmp .finish

  .wmcreate:
invoke GetDC,[hwnd]
mov [hdc],eax
mov edi,pfd
mov ecx,sizeof.PIXELFORMATDESCRIPTOR shr 2
xor eax,eax
rep stosd
mov [pfd.nSize],sizeof.PIXELFORMATDESCRIPTOR
mov [pfd.nVersion],1
mov [pfd.dwFlags],PFD_SUPPORT_OPENGL+PFD_DOUBLEBUFFER+PFD_DRAW_TO_WINDOW
mov [pfd.dwLayerMask],PFD_MAIN_PLANE
mov [pfd.iPixelType],PFD_TYPE_RGBA
mov [pfd.cColorBits],32
mov [pfd.cDepthBits],32
mov [pfd.cAccumBits],0
mov [pfd.cStencilBits],0
invoke ChoosePixelFormat,[hdc],pfd
invoke SetPixelFormat,[hdc],eax,pfd
invoke wglCreateContext,[hdc]
mov [hrc],eax
invoke wglMakeCurrent,[hdc],[hrc]
invoke GetClientRect,[hwnd],rc
invoke glViewport,0,0,[rc.right],[rc.bottom]
xor eax,eax
jmp .finish

  .wmsize:
invoke GetClientRect,[hwnd],rc
invoke glViewport,0,0,[rc.right],[rc.bottom]
invoke InvalidateRect,[hwnd],NULL,FALSE
xor eax,eax
jmp .finish

  .wmactivateapp:
push [wmsg]
pop [active]
xor eax,eax
jmp .finish

  .wmpaint:
invoke glClear,GL_COLOR_BUFFER_BIT
invoke glRotatef, 1.0, 0.0, 0.0, 1.0
invoke glBegin,GL_QUADS
invoke glColor3f,  0.0, 1.0, 1.0
invoke glVertex3f,-0.5,-0.5,-0.5
invoke glColor3f,  1.0, 0.0, 1.0
invoke glVertex3f, 0.5,-0.5,-0.5
invoke glColor3f,  1.0, 1.0, 0.0
invoke glVertex3f, 0.5, 0.5,-0.5
invoke glColor3f,  0.0, 0.0, 1.0
invoke glVertex3f,-0.5, 0.5,-0.5
invoke glEnd
invoke SwapBuffers,[hdc]
xor eax,eax
jmp .finish

  .wmkeydown:
cmp [wparam],VK_ESCAPE
jne .defwndproc

  .wmdestroy:
invoke wglMakeCurrent,0,0
invoke wglDeleteContext,[hrc]
invoke ReleaseDC,[hwnd],[hdc]
invoke PostQuitMessage,0
xor eax,eax

  .finish:
pop edi esi ebx
ret
endp




section '.idata' import data readable writeable
  library kernel,'KERNEL32.DLL',\
  user,'USER32.DLL',\
  gdi,'GDI32.DLL',\
  opengl,'OPENGL32.DLL'

  import kernel,\
GetModuleHandle,'GetModuleHandleA',\
ExitProcess,'ExitProcess'

  import user,\
RegisterClass,'RegisterClassA',\
CreateWindowEx,'CreateWindowExA',\
DefWindowProc,'DefWindowProcA',\
GetMessage,'GetMessageA',\
TranslateMessage,'TranslateMessage',\
DispatchMessage,'DispatchMessageA',\
LoadCursor,'LoadCursorA',\
LoadIcon,'LoadIconA',\
GetClientRect,'GetClientRect',\
InvalidateRect,'InvalidateRect',\
GetDC,'GetDC',\
ReleaseDC,'ReleaseDC',\
PostQuitMessage,'PostQuitMessage'

  import gdi,\
ChoosePixelFormat,'ChoosePixelFormat',\
SetPixelFormat,'SetPixelFormat',\
SwapBuffers,'SwapBuffers'

  import opengl,\
wglCreateContext,'wglCreateContext',\
wglMakeCurrent,'wglMakeCurrent',\
glViewport,'glViewport',\
glClear,'glClear',\
glRotatef,'glRotatef',\
glBegin,'glBegin',\
glColor3f,'glColor3f',\
glVertex3f,'glVertex3f',\
glEnd,'glEnd',\
wglDeleteContext,'wglDeleteContext'



Challenge Trophies Won:

Offline Shockwave

  • good/evil
  • Founder Member
  • DBF Aficionado
  • ********
  • Posts: 17334
  • Karma: 497
  • evil/good
    • View Profile
    • My Homepage
Re: OpenGL Example Full Screen
« Reply #1 on: April 03, 2008 »
K+ I'd forgotten all about these examples in Fasm :)
Shockwave ^ Codigos
Challenge Trophies Won:

Offline Jim

  • Founder Member
  • DBF Aficionado
  • ********
  • Posts: 5293
  • Karma: 400
    • View Profile
Re: OpenGL Example Full Screen
« Reply #2 on: April 03, 2008 »
Nice!  It would be great to see an asm OpenGL sample optimised for size, right now the C framework we have will generate significantly smaller code than this!

Jim
Challenge Trophies Won:

Offline rain_storm

  • Here comes the Rain
  • DBF Aficionado
  • ******
  • Posts: 3084
  • Karma: 182
  • Rain never hurt nobody
    • View Profile
    • org_100h
Re: OpenGL Example Full Screen
« Reply #3 on: April 04, 2008 »
C framework smaller than this ... is that with compression or not?

Best I can manage is 2.5K at the moment and I only achieve that by declaring a single flat section that contains imports, data and code instead of separate sections for each but I think the imports still get their own section regardless.

I have been looking through Tyler Dyrdens 1K OGL stuff but its way over my head. He does a whole lotta manipulation to the PE header to strip out everything and it is nearly impossible to understand

Challenge Trophies Won:

Offline Jim

  • Founder Member
  • DBF Aficionado
  • ********
  • Posts: 5293
  • Karma: 400
    • View Profile
Re: OpenGL Example Full Screen
« Reply #4 on: April 04, 2008 »
Code: [Select]
mov [pfd.nSize],sizeof.PIXELFORMATDESCRIPTOR
mov [pfd.nVersion],1
mov [pfd.dwFlags],PFD_SUPPORT_OPENGL+PFD_DOUBLEBUFFER+PFD_DRAW_TO_WINDOW
mov [pfd.dwLayerMask],PFD_MAIN_PLANE
mov [pfd.iPixelType],PFD_TYPE_RGBA
mov [pfd.cColorBits],32
mov [pfd.cDepthBits],32
mov [pfd.cAccumBits],0
mov [pfd.cStencilBits],0
It's this kind of stuff that's bloating it.  Why not just store those values in the data segment instead of writing code to fill them in?  That would be less than half the size.

Jim
Challenge Trophies Won:

Offline rain_storm

  • Here comes the Rain
  • DBF Aficionado
  • ******
  • Posts: 3084
  • Karma: 182
  • Rain never hurt nobody
    • View Profile
    • org_100h
Re: OpenGL Example Full Screen
« Reply #5 on: April 05, 2008 »
Thats a good idea, never thought about that one thanks for the tip

Edit:
You're right down to 2K thanks a lot Jim K++

« Last Edit: April 05, 2008 by rain_storm »

Challenge Trophies Won:

Offline rbz

  • Founder Member
  • DBF Aficionado
  • ********
  • Posts: 2484
  • Karma: 427
    • View Profile
    • http://www.rbraz.com/
Re: OpenGL Example Full Screen
« Reply #6 on: April 05, 2008 »
Could be done in 1536 (framework) bytes exe  ;)

Hint: Do you really need "WindowProc" ? :)
rbz ^ Codigos
Challenge Trophies Won:

Offline rain_storm

  • Here comes the Rain
  • DBF Aficionado
  • ******
  • Posts: 3084
  • Karma: 182
  • Rain never hurt nobody
    • View Profile
    • org_100h
Re: OpenGL Example Full Screen
« Reply #7 on: April 05, 2008 »
Cant quite strip the WindowProc outta this one but I have reduced it to a simple return and now its down to 1.5K so thanks for the tip rbz K+. can I get some tips on what to do to remove the windowProc altogether. It doesnt work when I strip it out in fact I have to open task manager to even see it runnin and to close it.

Challenge Trophies Won:

Offline rbz

  • Founder Member
  • DBF Aficionado
  • ********
  • Posts: 2484
  • Karma: 427
    • View Profile
    • http://www.rbraz.com/
Re: OpenGL Example Full Screen
« Reply #8 on: April 07, 2008 »
Just return from "WindowProc" is wrong and doesn't work here

To get rid of "WindowProc", first get rid of "RegisterClass" and use a standard win32 class - "edit"
To initialize your window you can use this line:
Code: [Select]
invoke CreateWindowEx,WS_EX_TOPMOST,_class,0,WS_VISIBLE+WS_POPUP+WS_MAXIMIZE,0,0,0,0,0,0,0,0
To exit from your main draw loop, use "GetAsyncKeyState"

This is all you need for a small asm framework :)
rbz ^ Codigos
Challenge Trophies Won:

Offline rain_storm

  • Here comes the Rain
  • DBF Aficionado
  • ******
  • Posts: 3084
  • Karma: 182
  • Rain never hurt nobody
    • View Profile
    • org_100h
Re: OpenGL Example Full Screen
« Reply #9 on: June 23, 2008 »
Great tip rbz it took a while to sink in (and a whole lotta reading) to be honest the whole API interface I just didnt get it didnt know where I should be putting the effort in. The main problem I was having was with the windows message system. I thought that it was unneccessary meddling by the OS using GetAsyncKeyState is soo useful. Got it down to 1.5k with roation in there and all now. :D

Code: [Select]
; OpenGL programming example
 format  PE GUI 4.0
 entry   start
 include 'win32a.inc'
 include 'opengl32.inc'

 RESX = 640
 RESY = 480

 FULLSCREEN = WS_VISIBLE+WS_MAXIMIZE+WS_POPUP
 WINDOW = WS_VISIBLE+WS_OVERLAPPEDWINDOW+WS_CLIPCHILDREN+WS_CLIPSIBLINGS

  start:invoke  CreateWindowEx,WS_EX_TOPMOST,_class,0,WS_VISIBLE+WS_POPUP+WS_MAXIMIZE,0,0,0,0,0,0,0,0
        invoke  GetDC,eax
        xchg    eax,ebp
        invoke  ChoosePixelFormat,ebp,pfd
        invoke  SetPixelFormat,ebp,eax,pfd
        invoke  wglCreateContext,ebp
        invoke  wglMakeCurrent,ebp,eax
  msg_loop:
        invoke  glClear,GL_COLOR_BUFFER_BIT
        invoke  glRotatef,[theta],0.0,0.0,1.0
         invoke  glBegin,GL_QUADS
                invoke  glColor3f,  1.0, 0.5, 0.5
                invoke  glVertex3f,-0.5,-0.5,-0.5
                invoke  glVertex3f, 0.5,-0.5,-0.5
                invoke  glColor3f,  0.5, 0.5, 1.0
                invoke  glVertex3f, 0.5, 0.5,-0.5
                invoke  glVertex3f,-0.5, 0.5,-0.5
        invoke  glEnd
        invoke  SwapBuffers,ebp
        invoke  GetAsyncKeyState,VK_ESCAPE
        or      eax,eax
        jz      msg_loop
  end_loop:
        invoke  ExitProcess,NULL
  _class db 'EDIT',0
  theta GLfloat 0.6
  pfd PIXELFORMATDESCRIPTOR 18,1,PFD_SUPPORT_OPENGL+PFD_DOUBLEBUFFER+PFD_DRAW_TO_WINDOW,PFD_MAIN_PLANE,PFD_TYPE_RGBA,32,32,0,0

  DATA IMPORT
  library kernel,'KERNEL32.DLL',\
          user,'USER32.DLL',\
          gdi,'GDI32.DLL',\
          opengl,'OPENGL32.DLL'
  import  kernel,\
          ExitProcess,'ExitProcess'
  import  user,\
          CreateWindowEx,'CreateWindowExA',\
          GetAsyncKeyState,'GetAsyncKeyState',\
          GetDC,'GetDC'
  import  gdi,\
          ChoosePixelFormat,'ChoosePixelFormat',\
          SetPixelFormat,'SetPixelFormat',\
          SwapBuffers,'SwapBuffers'
  import  opengl,\
          wglCreateContext,'wglCreateContext',\
          glRotatef,'glRotatef',\
          glBegin,'glBegin',\
          glColor3f,'glColor3f',\
          glVertex3f,'glVertex3f',\
          glEnd,'glEnd',\
          glClear,'glClear',\
          wglMakeCurrent,'wglMakeCurrent'
  END DATA

Edit - anyone know how to go about setting the section alignment to 4 instead of the default 512?
« Last Edit: June 23, 2008 by rain_storm »

Challenge Trophies Won:

Offline rbz

  • Founder Member
  • DBF Aficionado
  • ********
  • Posts: 2484
  • Karma: 427
    • View Profile
    • http://www.rbraz.com/
Re: OpenGL Example Full Screen
« Reply #10 on: June 24, 2008 »
Nice work, I use something like this

Quote
Edit - anyone know how to go about setting the section alignment to 4 instead of the default 512?
Do you mean "file alignment" ? If yes, I think 512 is fasm default value and I don't know if you can change it, if I remember there's a topic (fasm forum) about pe structure that you take a look.

If you mean data or code alignment you can use "align" command before your code.
rbz ^ Codigos
Challenge Trophies Won:

Offline AnimalMother

  • btst #6,$bfe001
  • Atari ST
  • ***
  • Posts: 113
  • Karma: 7
    • View Profile
Re: OpenGL Example Full Screen
« Reply #11 on: June 24, 2008 »
Hmm, I found an interesting link http://www.phreedom.org/solar/code/tinype/
Maybe it helps  8)

Offline rbz

  • Founder Member
  • DBF Aficionado
  • ********
  • Posts: 2484
  • Karma: 427
    • View Profile
    • http://www.rbraz.com/
Re: OpenGL Example Full Screen
« Reply #12 on: June 24, 2008 »
Thanks for this link, there is some good information in there
rbz ^ Codigos
Challenge Trophies Won:

Offline Jim

  • Founder Member
  • DBF Aficionado
  • ********
  • Posts: 5293
  • Karma: 400
    • View Profile
Re: OpenGL Example Full Screen
« Reply #13 on: June 25, 2008 »
What happens if you use crinkler to link this program rainstorm?  It will deal with minimum segment sizes automatically and compress the code/imports really well, usually around 2:1 compression for this kind of thing.

Jim
Challenge Trophies Won:

Offline rain_storm

  • Here comes the Rain
  • DBF Aficionado
  • ******
  • Posts: 3084
  • Karma: 182
  • Rain never hurt nobody
    • View Profile
    • org_100h
Re: OpenGL Example Full Screen
« Reply #14 on: June 25, 2008 »
@AnimalMother - Fantaistic Link it gave me some words to put into a search and I found this great pdf refernce to the structure of the PE format in a thread on FASM I attached it here, some great reading in there

@Jim - Lets find out shall we? What object file format does crinkler accept, I think I will go back to the FASM forum to see how to get FASM to output object files.

Challenge Trophies Won:

Offline rbz

  • Founder Member
  • DBF Aficionado
  • ********
  • Posts: 2484
  • Karma: 427
    • View Profile
    • http://www.rbraz.com/
Re: OpenGL Example Full Screen
« Reply #15 on: June 26, 2008 »
Quote
What object file format does crinkler accept
MSCOFF only :)

Use "format MS COFF" to compile your file, use "extrn" directive to define the external symbol for crinkler.
eg.:
Code: [Select]
extrn '__imp__MessageBoxA@16' as MessageBox:dword
rbz ^ Codigos
Challenge Trophies Won:

Offline rain_storm

  • Here comes the Rain
  • DBF Aficionado
  • ******
  • Posts: 3084
  • Karma: 182
  • Rain never hurt nobody
    • View Profile
    • org_100h
Re: OpenGL Example Full Screen
« Reply #16 on: June 26, 2008 »
Thanks rbz got the obj file now just waitin on the SDK to download on this system (my own system is back at the family home atm). Oh well while Im waitin for that to download I will have a go at manually compressing the image to see what are the differences between crinkler and bare metal assembly. Hopefully it wont take me that long.

Challenge Trophies Won:

Offline rain_storm

  • Here comes the Rain
  • DBF Aficionado
  • ******
  • Posts: 3084
  • Karma: 182
  • Rain never hurt nobody
    • View Profile
    • org_100h
Re: OpenGL Example Full Screen
« Reply #17 on: June 27, 2008 »
Okay this it manually formatted to PE format. Havent yet started to strip out the unused parts. Just putting it up here as it is actually very interesting source code for reading for anyone with an interest. I definately recommend doing this to anyone at intermediate level with asm. Its very low level but the stuff you learn makes it worthwhile and will take you from intermediate assembler to advanced assembler.

Challenge Trophies Won:

Offline rain_storm

  • Here comes the Rain
  • DBF Aficionado
  • ******
  • Posts: 3084
  • Karma: 182
  • Rain never hurt nobody
    • View Profile
    • org_100h
Re: OpenGL Example Full Screen
« Reply #18 on: June 29, 2008 »
Great news crinkler has gotten this down to 673 bytes. bad news is that I have already gotten this down to 693 bytes by manually removing the Dos stub and interleaving the headers I still have to compress the imports table. When that is all done and tested I will probably be below 673 bytes

Edit - I got it down to 622 bytes by hand. Outperforming even the mighty crinkler. I surprised myself with how many overlaps I managed to get in there. in some cases a single byte is serving up to 4 purposes. only a couple of bytes in the header are used only once. The only problem is that it is not compressed Crinkler would outshine this meathod with its compression ratio. But for extreme size I think this meathod can be brought even further than I have come with it. maybe even < 600 bytes.

Edit2 - I dont think my coding style is compressing well at all I am certain that crinkler can do much better than this, I saw a 396 byte frame work by rbraz over at in4k.
« Last Edit: June 30, 2008 by rain_storm »

Challenge Trophies Won: