News:

Masm32 SDK description, downloads and other helpful links
Message to All Guests

Main Menu

Can't get a rendering context, wglCreateContext fails

Started by hamper, November 11, 2013, 10:30:52 PM

Previous topic - Next topic

hamper

I'm having a problem getting even a very simple OpenGL program to work. The problem is that the function wglCreateContext always fails, and returns zero. I can't see where the problem is, so can anyone spot where I'm going wrong? Help, please.
My system has no problem whatsoever running OpenGL .exe programs, so it can't be the video card or drivers etc.
And I've checked the program (with message boxes) up to the point where it fails, and everything seems to be working fine.
Getting exasperated.
Any ideas anyone?
Thanks in advance.


;--------------------------------------------------------------------------------------
; A simple OpenGL example                                                   ogltest.asm
;--------------------------------------------------------------------------------------

.686
.model flat,stdcall
option casemap:none

includelib user32
includelib kernel32
includelib opengl32

;--------------------------------------------------------------------------------------

CreateWindowExA      proto :dword,:dword,:dword,:dword,:dword,:dword,
                           :dword,:dword,:dword,:dword,:dword,:dword
DefWindowProcA       proto :dword,:dword,:dword,:dword
DispatchMessageA     proto :dword
ExitProcess          proto :dword
GetMessageA          proto :dword,:dword,:dword,:dword
GetModuleHandleA     proto :dword
LoadCursorA          proto :dword,:dword
LoadIconA            proto :dword,:dword
PostQuitMessage      proto :dword
RegisterClassExA     proto :dword
windowproc           proto :dword,:dword,:dword,:dword
GetDC                proto :dword
wglChoosePixelFormat proto :dword,:dword
wglSetPixelFormat    proto :dword,:sdword,:dword
wglCreateContext     proto :dword
wglMakeCurrent       proto :dword,:dword
wglDeleteContext     proto :dword
ReleaseDC            proto :dword,:dword
glBegin              proto :dword
glEnd                proto
glVertex2fv          proto :dword
MessageBoxA          proto :dword,:dword,:dword,:dword

point struct
   x dword ?
   y dword ?
point ends

msgst struct
   hwnd    dword ?
   message dword ?
   wparam  dword ?
   lparam  dword ?
   time    dword ?
   pt      point <>
msgst ends

windowclasstype struct
   wcsize        dword ?
   style         dword ?
   addrwp        dword ?
   classeb       dword ?
   windoweb      dword ?
   proghandle    dword ?
   liconhandle   dword ?
   cursorhandle  dword ?
   colour        dword ?
   menuhandle    dword ?
   addrclassname dword ?
   siconhandle   dword ?
windowclasstype ends

pfdtype struct
   nsize           word  40
   nversion        word  1
   dwflags         dword 36   ; PFD_DRAW_TO_WINDOW + PFD_SUPPORT_OPENGL
   ipixeltype      byte  0
   ccolorbits      byte  32
   credbits        byte  0
   credshift       byte  0
   cgreenbits      byte  0
   cgreenshift     byte  0
   cbluebits       byte  0
   cblueshift      byte  0
   calphabits      byte  0
   calphashift     byte  0
   caccumbits      byte  0
   caccumredbits   byte  0
   caccumgreenbits byte  0
   caccumbluebits  byte  0
   caccumalphabits byte  0
   cdepthbits      byte  32
   cstencilbits    byte  0
   cauxbuffers     byte  0
   ilayertype      byte  0
   breserved       byte  0
   dwlayermask     dword 0
   dwvisiblemask   dword 0
   dwdamagemask    dword 0
pfdtype ends

;--------------------------------------------------------------------------------------

.const
classname   byte "SimpleWinClass",0
windowtitle byte "The window title",0
mymbtitle   byte "Alert",0
mymbtext    byte "Could not get rendering context",0

.data?
msg       msgst <>
mywc      windowclasstype <>
winhandle dword ?
dchandle  dword ?
rchandle  dword ?

.data
pfd pfdtype <>
myvertex1 real4 0.0,0.0
myvertex2 real4 1.0,0.0
myvertex3 real4 0.5,0.87

.code
start:

;######################################################################################

;---------- fill up the window class structure variable and get the program handle etc.

mov mywc.wcsize,48
mov mywc.style,35                    ; CS_VREDRAW + CS_HREDRAW + CS_OWNDC
mov mywc.addrwp,offset windowproc
mov mywc.classeb,0
mov mywc.windoweb,0
push 0
call GetModuleHandleA
mov mywc.proghandle,eax
push 32515                           ; A black ! in a yellow triangle
push 0
call LoadIconA
mov mywc.liconhandle,eax
mov mywc.siconhandle,eax
push 32515                           ; A crosshair
push 0
call LoadCursorA
mov mywc.cursorhandle,eax
mov mywc.colour,2                    ; desktop colour
mov mywc.menuhandle,0
mov mywc.addrclassname,offset classname

;---------- register the window class

push offset mywc
call RegisterClassExA

;---------- create and display the window

push 0
push mywc.proghandle
push 0
push 0
push 340                           ; window height
push 320                           ; window width
push 230                           ; window top position
push 480                           ; window left position
push 269418496                     ; WS_VISIBLE + title bar, title, icon, icon menu,
                                   ;    min, max and close buttons, sizing borders
push offset windowtitle
push mywc.addrclassname
push 0                             ; default
call CreateWindowExA
mov winhandle,eax

;---------- get a device context

push winhandle
call GetDC
mov dchandle,eax

;---------- choose pixel format

push offset pfd
push dchandle
call wglChoosePixelFormat

;---------- set pixel format

push offset pfd
push eax
push dchandle
call wglSetPixelFormat

;---------- get rendering context (** FAILS **)

push dchandle
call wglCreateContext
mov  rchandle,eax


cmp eax,0
jne sofarsogood

push 0
push offset mymbtitle
push offset mymbtext
push 0
call MessageBoxA

sofarsogood:

; program WOULD now continue, but doesn't get this far

GoneFishing

Hi hamper,
It would be better if you posted the complete source code so we can reproduce the problem on our machines
and find out what's going wrong there .
You may use "code" tags to incapsulate your code into the post .

Take a look into the \MASM32\examples\exampl04\opengl example folder . Maybe it gives you some idea .

EDIT: pay attention to WM_CREATE handling routine of window procedure in the example code 

hamper

;--------------------------------------------------------------------------------------
; A simple OpenGL example                                                   ogltest.asm
;--------------------------------------------------------------------------------------

.686
.model flat,stdcall
option casemap:none

includelib user32
includelib kernel32
includelib opengl32

;--------------------------------------------------------------------------------------

CreateWindowExA      proto :dword,:dword,:dword,:dword,:dword,:dword,
                           :dword,:dword,:dword,:dword,:dword,:dword
DefWindowProcA       proto :dword,:dword,:dword,:dword
DispatchMessageA     proto :dword
ExitProcess          proto :dword
GetMessageA          proto :dword,:dword,:dword,:dword
GetModuleHandleA     proto :dword
LoadCursorA          proto :dword,:dword
LoadIconA            proto :dword,:dword
PostQuitMessage      proto :dword
RegisterClassExA     proto :dword
windowproc           proto :dword,:dword,:dword,:dword
GetDC                proto :dword
wglChoosePixelFormat proto :dword,:dword
wglSetPixelFormat    proto :dword,:sdword,:dword
wglCreateContext     proto :dword
wglMakeCurrent       proto :dword,:dword
wglDeleteContext     proto :dword
ReleaseDC            proto :dword,:dword
glBegin              proto :dword
glEnd                proto
glVertex2fv          proto :dword
MessageBoxA          proto :dword,:dword,:dword,:dword

point struct
   x dword ?
   y dword ?
point ends

msgst struct
   hwnd    dword ?
   message dword ?
   wparam  dword ?
   lparam  dword ?
   time    dword ?
   pt      point <>
msgst ends

windowclasstype struct
   wcsize        dword ?
   style         dword ?
   addrwp        dword ?
   classeb       dword ?
   windoweb      dword ?
   proghandle    dword ?
   liconhandle   dword ?
   cursorhandle  dword ?
   colour        dword ?
   menuhandle    dword ?
   addrclassname dword ?
   siconhandle   dword ?
windowclasstype ends

pfdtype struct
   nsize           word  40
   nversion        word  1
   dwflags         dword 36   ; PFD_DRAW_TO_WINDOW + PFD_SUPPORT_OPENGL
   ipixeltype      byte  0
   ccolorbits      byte  32
   credbits        byte  0
   credshift       byte  0
   cgreenbits      byte  0
   cgreenshift     byte  0
   cbluebits       byte  0
   cblueshift      byte  0
   calphabits      byte  0
   calphashift     byte  0
   caccumbits      byte  0
   caccumredbits   byte  0
   caccumgreenbits byte  0
   caccumbluebits  byte  0
   caccumalphabits byte  0
   cdepthbits      byte  32
   cstencilbits    byte  0
   cauxbuffers     byte  0
   ilayertype      byte  0
   breserved       byte  0
   dwlayermask     dword 0
   dwvisiblemask   dword 0
   dwdamagemask    dword 0
pfdtype ends

;--------------------------------------------------------------------------------------

.const
classname   byte "SimpleWinClass",0
windowtitle byte "The window title",0
mymbtitle   byte "Alert",0
mymbtext    byte "Could not get rendering context",0

.data?
msg       msgst <>
mywc      windowclasstype <>
winhandle dword ?
dchandle  dword ?
rchandle  dword ?

.data
pfd pfdtype <>
myvertex1 real4 0.0,0.0
myvertex2 real4 1.0,0.0
myvertex3 real4 0.5,0.87

.code
start:

;######################################################################################

;---------- fill up the window class structure variable and get the program handle etc.

mov mywc.wcsize,48
mov mywc.style,35                    ; CS_VREDRAW + CS_HREDRAW + CS_OWNDC
mov mywc.addrwp,offset windowproc
mov mywc.classeb,0
mov mywc.windoweb,0
push 0
call GetModuleHandleA
mov mywc.proghandle,eax
push 32515                           ; A black ! in a yellow triangle
push 0
call LoadIconA
mov mywc.liconhandle,eax
mov mywc.siconhandle,eax
push 32515                           ; A crosshair
push 0
call LoadCursorA
mov mywc.cursorhandle,eax
mov mywc.colour,2                    ; desktop colour
mov mywc.menuhandle,0
mov mywc.addrclassname,offset classname

;---------- register the window class

push offset mywc
call RegisterClassExA

;---------- create and display the window

push 0
push mywc.proghandle
push 0
push 0
push 340                           ; window height
push 320                           ; window width
push 230                           ; window top position
push 480                           ; window left position
push 269418496                     ; WS_VISIBLE + title bar, title, icon, icon menu,
                                   ;    min, max and close buttons, sizing borders
push offset windowtitle
push mywc.addrclassname
push 0                             ; default
call CreateWindowExA
mov winhandle,eax

;---------- get a device context

push winhandle
call GetDC
mov dchandle,eax

;---------- choose pixel format

push offset pfd
push dchandle
call wglChoosePixelFormat

;---------- set pixel format

push offset pfd
push eax
push dchandle
call wglSetPixelFormat

;---------- get rendering context (** FAILS **)

push dchandle
call wglCreateContext
mov  rchandle,eax


cmp eax,0
jne sofarsogood

push 0
push offset mymbtitle
push offset mymbtext
push 0
call MessageBoxA

sofarsogood:

; program WOULD now continue, but doesn't get this far

push rchandle
push dchandle
call wglMakeCurrent

push 4                  ; triangles
call glBegin
push offset myvertex1
call glVertex2fv
push offset myvertex2
call glVertex2fv
push offset myvertex3
call glVertex2fv
call glEnd

msgloopstart:
push 0
push 0
push winhandle
push offset msg
call GetMessageA
cmp eax,0
je msgloopend
push offset msg
call DispatchMessageA
jmp msgloopstart
msgloopend:
push 0
call ExitProcess

;######################################################################################

;---------- the window procedure

windowproc proc hwnd:dword,message:dword,wparam:dword,lparam:dword

cmp message,16 ; WM_CLOSE
je its16

; default processing
push lparam
push wparam
push message
push hwnd
call DefWindowProcA
ret

its16:
   push rchandle
   call wglDeleteContext
   push dchandle
   push winhandle
   call ReleaseDC
push 0
call PostQuitMessage
ret

windowproc endp

;--------------------------------------------------------------------------------------

end start

GoneFishing

Thanks hamper  :t
much better

Look what I did:
Quote
;---------- get rendering context (** FAILS **)

push dchandle
call wglCreateContext
mov  rchandle,eax

    push MB_OK
    push offset mymbtitle
    push LastError$()
    push 0
    call MessageBox


cmp eax,0
jne sofarsogood

push 0
push offset mymbtitle
push offset mymbtext
push 0
call MessageBoxA

and what I got:
QuoteThe pixel format is invalid

Think  :t

hamper

Ok, but any ideas why?
The functions wglChoosePixelFormat and wglSetPixelFormat don't return with any errors.
I also tried various combinations of values in the elements of the pfd, but nothing made any difference.
So at the moment I'm none the wiser, and still searching for the solution.

GoneFishing

Did you try to declare pfd like that?:
pfd PIXELFORMATDESCRIPTOR <>
Ok, no one here but you can make you wiser  ;)
Did you compared your source code with that in opengl example? Are there any differences?
Well, I intermixed them a little and made wglCreateContext  return status SUCCESS:

;--------------------------------------------------------------------------------------
; A simple OpenGL example                                                   ogltest.asm
;--------------------------------------------------------------------------------------

include \masm32\include\masm32rt.inc

includelib \masm32\lib\opengl32.lib

;--------------------------------------------------------------------------------------

CreateWindowExA      proto :dword,:dword,:dword,:dword,:dword,:dword,
                           :dword,:dword,:dword,:dword,:dword,:dword
DefWindowProcA       proto :dword,:dword,:dword,:dword
DispatchMessageA     proto :dword
ExitProcess          proto :dword
GetMessageA          proto :dword,:dword,:dword,:dword
GetModuleHandleA     proto :dword
LoadCursorA          proto :dword,:dword
LoadIconA            proto :dword,:dword
PostQuitMessage      proto :dword
RegisterClassExA     proto :dword
windowproc           proto :dword,:dword,:dword,:dword
GetDC                proto :dword
wglChoosePixelFormat proto :dword,:dword
wglSetPixelFormat    proto :dword,:sdword,:dword
wglCreateContext     proto :dword
wglMakeCurrent       proto :dword,:dword
wglDeleteContext     proto :dword
ReleaseDC            proto :dword,:dword
glBegin              proto :dword
glEnd                proto
glVertex2fv          proto :dword
MessageBoxA          proto :dword,:dword,:dword,:dword

point struct
   x dword ?
   y dword ?
point ends

msgst struct
   hwnd    dword ?
   message dword ?
   wparam  dword ?
   lparam  dword ?
   time    dword ?
   pt      point <>
msgst ends

windowclasstype struct
   wcsize        dword ?
   style         dword ?
   addrwp        dword ?
   classeb       dword ?
   windoweb      dword ?
   proghandle    dword ?
   liconhandle   dword ?
   cursorhandle  dword ?
   colour        dword ?
   menuhandle    dword ?
   addrclassname dword ?
   siconhandle   dword ?
windowclasstype ends

;--------------------------------------------------------------------------------------

.const
classname   byte "SimpleWinClass",0
windowtitle byte "The window title",0
mymbtitle   byte "Alert",0
mymbtext    byte "Could not get rendering context",0

.data?
msg       msgst <>
mywc      windowclasstype <>
winhandle dword ?
dchandle  dword ?
rchandle  dword ?

.data

PixFrm PIXELFORMATDESCRIPTOR <>
myvertex1 real4 0.0,0.0
myvertex2 real4 1.0,0.0
myvertex3 real4 0.5,0.87

.code
start:

;######################################################################################

;---------- fill up the window class structure variable and get the program handle etc.

mov mywc.wcsize,48
mov mywc.style,35                    ; CS_VREDRAW + CS_HREDRAW + CS_OWNDC
mov mywc.addrwp,offset windowproc
mov mywc.classeb,0
mov mywc.windoweb,0
push 0
call GetModuleHandleA
mov mywc.proghandle,eax
push 32515                           ; A black ! in a yellow triangle
push 0
call LoadIconA
mov mywc.liconhandle,eax
mov mywc.siconhandle,eax
push 32515                           ; A crosshair
push 0
call LoadCursorA
mov mywc.cursorhandle,eax
mov mywc.colour,2                    ; desktop colour
mov mywc.menuhandle,0
mov mywc.addrclassname,offset classname

;---------- register the window class

push offset mywc
call RegisterClassExA

;---------- create and display the window

push 0
push mywc.proghandle
push 0
push 0
push 340                           ; window height
push 320                           ; window width
push 230                           ; window top position
push 480                           ; window left position
push 269418496                     ; WS_VISIBLE + title bar, title, icon, icon menu,
                                   ;    min, max and close buttons, sizing borders
push offset windowtitle
push mywc.addrclassname
push 0                             ; default
call CreateWindowExA
mov winhandle,eax

invoke ShowWindow,winhandle,SW_SHOWNORMAL
invoke UpdateWindow,winhandle
call       DoEvents
ret



;######################################################################################

DoEvents PROC
LOCAL m:MSG
StartLoop: ; Check for waiting messages
invoke PeekMessage,ADDR m,0,0,0,PM_NOREMOVE
or eax,eax
jz NoMsg
invoke GetMessage,ADDR m,NULL,0,0
or eax,eax
jz ExitLoop
invoke TranslateMessage,ADDR m
invoke DispatchMessage,ADDR m
jmp StartLoop
NoMsg: ; No pending messages: draw the scene
;invoke DrawScene
jmp StartLoop
ExitLoop: mov eax,m.wParam
ret
DoEvents ENDP

;----------

comment *

DrawScene proc

YOUR DRAWING CODE HERE ;-)

DrawScene endp

*

;---------- the window procedure

windowproc  PROC hWin:DWORD,uMsg:DWORD,wParam:DWORD,lParam:DWORD
LOCAL WINRect:RECT
LOCAL PixFormat:DWORD

.if uMsg == WM_CREATE
invoke GetDC,hWin
mov dchandle,eax
mov ax,SIZEOF PixFrm
mov PixFrm.nSize,ax
mov PixFrm.nVersion,1
mov PixFrm.dwFlags,PFD_DRAW_TO_WINDOW or PFD_SUPPORT_OPENGL or PFD_DOUBLEBUFFER
mov PixFrm.dwLayerMask,PFD_MAIN_PLANE
mov PixFrm.iPixelType,PFD_TYPE_RGBA
mov PixFrm.cColorBits,8
mov PixFrm.cDepthBits,16
mov PixFrm.cAccumBits,0
mov PixFrm.cStencilBits,0
invoke ChoosePixelFormat,dchandle,ADDR PixFrm
mov PixFormat,eax
invoke SetPixelFormat,dchandle,PixFormat,ADDR PixFrm
or eax,eax
jz NoPixelFmt
invoke wglCreateContext,dchandle
mov rchandle,eax
                        fn MessageBox,0,LastError$(),"Last Error Text",MB_OK


NoPixelFmt:
return 0

.elseif uMsg == WM_SIZE
invoke GetClientRect,hWin,ADDR WINRect

return 0

.elseif uMsg == WM_CLOSE

mov eax,rchandle
or eax,eax
jz NoGlDC
; Delete our objects
invoke  wglDeleteContext,rchandle
                        invoke  ExitProcess,0
NoGlDC:
      invoke ReleaseDC,hWin,dchandle
      invoke DestroyWindow,hWin
return 0
.elseif uMsg == WM_DESTROY
invoke PostQuitMessage,NULL
return 0
.endif
invoke DefWindowProc,hWin,uMsg,wParam,lParam
ret

windowproc endp

;--------------------------------------------------------------------------------------

end start


runs a bit slowly 

hamper

I thank you for your efforts vertograd, but it doesn't leave me any the wiser.

Sure, I'm using my own names for things, like the pixel format descriptor structure type and the structure variable, but that shouldn't make any difference so long as the structure itself is properly defined, contains all the right elements in the right data types, and is correctly initialised - which I think it all is, unless you can spot an error somewhere?

And sure, I could just copy and paste one of the numerous example programs, then assemble it and it will probably work. But that's not really the point is it? I spent ages learning C, then ages learning assembly language, then ages more learning the Windows API and how to get a window operating on the desktop in both C and assembly language, and am now trying to learn how to program graphics using OpenGL. None of this is for profit, or for business reasons - just out of a personal interest in trying to learn things that I didn't know before.

I don't need double-buffering (yet) because all I'm trying to do is render a simple triangle into a window. I hope to expand into selecting (non-default) matrix modes, pushing and popping the matrix stack, performing transformations, and getting coloured perspective views etc. fairly soon, I hope. But for the moment I can't get even a triangle up :icon_redface:

So if I just want to draw a spinning, multi-coloured triangle and learn nothing about WHY it works, I could just fire up my C compiler with an example program designed by someone else, and call it that - done, so now put it all away.

Please don't think I'm being critical - I'm not, and I DO greatly appreciate your efforts. But what I really could do with some help on is whereabouts in MY program the fault lies.

Thanks

GoneFishing

Quote... So if I just want to draw a spinning, multi-coloured triangle and learn nothing about WHY it works, I could just fire up my C compiler with an example program designed by someone else ...
IMO it's probably the best way to start with opengl ...
Some time ago I started with DirectX in that manner . I found 4 tutorials from DirectX SDK translated into MASM:
Creating device
Rendering simple multicolored triangle, then spinning triangle  and so on
From them I knew about the structure of graphics application which has Init, Draw / Render,Cleanup routines etc.

... and it was a real fight with my first triangle ... and I won it  ;)

dedndave

first, use INVOKE rather than PUSH/PUSH/CALL
much easier to read - and much easier to debug   :t

second, rather than initializing the values of the pfd structure in the definition, do it in the data section
also - use the already defined structure and constants
    .DATA

pfd PIXELFORMATDESCRIPTOR <sizeof PIXELFORMATDESCRIPTOR,1,PFD_DRAW_TO_WINDOW or PFD_SUPPORT_OPENGL,PFD_TYPE_RGBA,32,,,,,,,,,,,,,,32,,,,,PFD_MAIN_PLANE,,>

otherwise, you can define pfd in the uninitialized data section and initialize it with code
the values you are currently using are most likely the reason the call is failing
it will be much easier to troubleshoot and update if you use the standard structure and constants

finally, rather than performing the OGL initialization in the main proc, between CreateWindowEx and the message loop,
perform it when the WndProc receives the WM_CREATE message
once the window has been created, it needs a message loop running to process messages

just because ChoosePixelFormat and SetPixelFormat are happy, doesn't mean wglCreateContext will be
they may very well accept values that CreateContext will not

hamper

"second, rather than initializing the values of the pfd structure in the definition, do it in the data section"
I understood that if values were assigned to structure elements in the declaration, then those values would become the default values when the variable is subsequently defined using <>. Are you saying that's incorrect?

PFD_MAIN_PLANE is the default (0) anyway.
PFD_TYPE_RGBA is the default (0) anyway.
Both are symbolic constants that simply get replaced by the actual values (0) by the preprocessor, as I understand it, so stating 0 has exactly the same effect as stating PFD_MAIN_PLANE does it not?

I always seem to come in for a lot of criticism because I prefer to use my own labels and tags, and because I prefer to use pushes and calls rather than the invoke method.
But apart from the fact that you don't like my programming "style", can you shed any light on my programming "content", and where the problem lies?

hamper

"just because ChoosePixelFormat and SetPixelFormat are happy, doesn't mean wglCreateContext will be
they may very well accept values that CreateContext will not"

Such as? The program content is fully presented, up to the point where the problem lies. Does anything stand out that would cause wglCreateContext to fail even though the pixel format is successfully chosen and set?

dedndave

 :biggrin:
when it comes to "style", you are preaching to the choir - lol
i much prefer to do things my own way - much like you
i learned assembly back in the 70's - much like you

but, over time, i have found that certain things are easier "the other way"
it's ok to add that to your learning curve

as for specific content, i am writing a little code of my own, at the moment
i want to see where the problem lies
in order for me to debug your code, i need to be able to read and understand it
so, i am writing a simple window program that creates the context and deletes it when the window is destroyed
and that's all it does
when i have it up and running, i can substitute pieces of your code to see where it fails

hamper

Well, if it helps this is my bog standard "get a simple window up on the desktop" program.
But you won't like it :eusa_snooty:


;--------------------------------------------------------------------------------------
; A simple window                                                      simplewindow.asm
;--------------------------------------------------------------------------------------

.686
.model flat,stdcall
option casemap:none

includelib user32
includelib kernel32

;--------------------------------------------------------------------------------------

CreateWindowExA  proto :dword,:dword,:dword,:dword,:dword,:dword,
                       :dword,:dword,:dword,:dword,:dword,:dword
DefWindowProcA   proto :dword,:dword,:dword,:dword
DispatchMessageA proto :dword
ExitProcess      proto :dword
GetMessageA      proto :dword,:dword,:dword,:dword
GetModuleHandleA proto :dword
LoadCursorA      proto :dword,:dword
LoadIconA        proto :dword,:dword
PostQuitMessage  proto :dword
RegisterClassExA proto :dword
windowproc       proto :dword,:dword,:dword,:dword

point struct
   x dword ?
   y dword ?
point ends

msgst struct
   hwnd    dword ?
   message dword ?
   wparam  dword ?
   lparam  dword ?
   time    dword ?
   pt      point <>
msgst ends

windowclasstype struct
   wcsize        dword ?
   style         dword ?
   addrwp        dword ?
   classeb       dword ?
   windoweb      dword ?
   proghandle    dword ?
   liconhandle   dword ?
   cursorhandle  dword ?
   colour        dword ?
   menuhandle    dword ?
   addrclassname dword ?
   siconhandle   dword ?
windowclasstype ends

;--------------------------------------------------------------------------------------

.const
classname   byte "SimpleWinClass",0
windowtitle byte "The window title",0

.data?
msg       msgst <>
mywc      windowclasstype <>
winhandle dword ?

.code
start:

;######################################################################################

;---------- fill up the window class structure variable and get the program handle etc.

mov mywc.wcsize,48
mov mywc.style,3
mov mywc.addrwp,offset windowproc
mov mywc.classeb,0
mov mywc.windoweb,0
push 0
call GetModuleHandleA
mov mywc.proghandle,eax
push 32515
push 0
call LoadIconA
mov mywc.liconhandle,eax
mov mywc.siconhandle,eax
push 32515
push 0
call LoadCursorA
mov mywc.cursorhandle,eax
mov mywc.colour,2
mov mywc.menuhandle,0
mov mywc.addrclassname,offset classname

;---------- register the window class

push offset mywc
call RegisterClassExA

;---------- create and display the window

push 0
push mywc.proghandle
push 0
push 0
push 300         ; window height
push 500         ; window width
push 100         ; window top position
push 100         ; window left position
push 269418496
push offset windowtitle
push mywc.addrclassname
push 0
call CreateWindowExA
mov winhandle,eax

;---------- the message loop

msgloopstart:
push 0
push 0
push winhandle
push offset msg
call GetMessageA
cmp eax,0
je msgloopend
push offset msg
call DispatchMessageA
jmp msgloopstart
msgloopend:
push 0
call ExitProcess

;######################################################################################

;---------- the window procedure

windowproc proc hwnd:dword,message:dword,wparam:dword,lparam:dword

cmp message,16 ; WM_CLOSE
je its16

; default processing
push lparam
push wparam
push message
push hwnd
call DefWindowProcA
ret

its16:
push 0
call PostQuitMessage
ret

windowproc endp

;--------------------------------------------------------------------------------------

end start

dedndave

got that up and running - it displays a non-zero handle value
take a look...........

jj2007

Quote from: hamper on November 12, 2013, 05:19:25 AM
But you won't like it :eusa_snooty:

If you are a productive coder with this style, why not?
You might like \Masm32\examples\exampl07\slickhuh\slickhuh.asm ;-)