How to call a function in user32.dll

My goal is to find the width of the vertical scroll bar on an applications window. I’m using Clarion8.
I’ve gotten this far: According to Microsoft’s info, the function that may do what I need is the GetSystemMetrics function contained in the User32.dll file in the system32 folder.
In code, I think my call would be:
MyScrollBarWidth = GetSystenMetrics(SM_CXVSCROLL) !SM_CXVSCROLL equates to 2
So far, I’ve used Clarion’s Libmaker to open user32.dll and have verified that the GetSystemMetrics function is contained therein. I then experimented with the sample WinAPI app to create a WinAPI.clw file that contains the equate and prototype for the function. In that CLW file the reference is to ‘Windows.dll’, but that file can’t be found on my Windows 10 computer. After determining that the GetSystemMetrics function is in user32.dll, I edited the WinAPI.clw file, changing Windows.dll to user32.dll. I also determined that Clarion’s Win32.lib file contains a reference to GetSystemMetrics.
I’m having no luck in putting all this together. I found buried in the Clarion manuals a reference to adding the Win32.lib file to the Solution tree, and tried INCLUDEing the WinAPI.clw file in the Global Include section, bet only get errors when I try to compile.
So, clearly I’m missing something. Can someone give me whatever steps I need to get this all put together?
TIA

If you’re talking about something with MODULE(‘Windows.dll’), there’s really nothing significant about the name. You could call it MODULE(‘Ham Sandwich’) and it would still work, as long as the lib for the respective DLL is linked in.
The places where the name IS significant is where the MODULE is a source module. But for Windows API stuff, I usually just leave it blank, like MODULE(’’).

In global Map declare the function. It’s best to place all these in file like WinAPI.INC and Include(’ WinAPI.INC’) so you can reuse it in multiple apps.

Module('Windows')
        GetSystemMetrics(nIndex LONG),LONG,PASCAL,DLL(1)
End

To call:

SysMet_CaptionHeight = GetSystemMetrics(4 )  !   LONG    !SM_CYCAPTION=4 The height of a caption area, in pixels.
SysMet_BorderHeight  = GetSystemMetrics(32)  !   LONG    !SM_CXSIZEFRAME=32 SM_CXFRAME is the thickness of the horizontal border. Caption+Border*2
SysMet_BorderWidth   = GetSystemMetrics(33)  !   LONG    !SM_CYSIZEFRAME=33 SM_CYFRAME is the thickness of the vertical border. Width Need * 2

One thing that makes this work is Clarion includes Lib\Win32.LIB with most everything useful in WinAPI User32 Kernal32 etc. You can look at Lib\Win32.LIB in LibMaker to see what’s in it.

I have my own LibMaker based on Mark’s with more features:

Jeff –
Your explanation certainly clears up my confusion about the specified DLL in the WinAPI.clw file. Turns out, it was simpler than I thought. So, you’ve gotten me past that hump.
So, this now brings me to another dilemma: I was trying to get the width of the scroll bar to be able to modify the code from your (and Dave Harms) article re: List Totaling (ClarionMag v2n11). As your article points out, when a list displays a vertical scroll bar, the 1-line Total list no longer lines up correctly with the upper list. So, I figured the value returned by GetSystemMetrics would be zero if no scroll bar was visible, but would have a useable value when it was. That could then be used to modify the width of the Total list. From what I can now see, it appears the scroll bar width (17 pixels, from my test) is constant whether the VSB is visible or not. It seems Clarion hides the scroll bar when it’s not needed, but the width doesn’t really change. So it seems that approach won’t work.
Other than determining how many list box items will trigger the VSB to be displayed, and reducing the width of the Totals list accordingly when that’s reached, I don’t see a better way to do this. I have not discovered any list property that indicates if the VSB is visible or not. That would solve the problem, if such a property exists. I’ll keep searching.
Thanks again for you help.

You use the EIP method to measure the width of the last column in both the Main List and the Total List. If the Main List has a VScroll displayed I would think the EIP Width would be smaller. Adjust the width of the Total list by the Delta?

In the LIST Format did you set all your Columns to FIXED so the User cannot HScroll them with Arrows?

You can use winapi classes, in this example TSystemMetrics class:

  PROGRAM

  INCLUDE('winapi.inc')

  MAP
  END

sm                            TSystemMetrics

  CODE
  MESSAGE('The width of a vertical scroll bar, in pixels: '& sm.CxVScroll())

Direct link to winapi zip: https://github.com/mikeduglas/winapi/archive/master.zip. Internally it uses printf module.

Mike -
Thanks for your input. I downloaded the zip file you referenced, unzipped it and placed the lib and libsrc files in the appropriate folders. I duplicated your sample program in a solution, but when I compile it, I get the error:
Error(3): cif$fileopen winapi.inc The system cannot find the path specified.
It seems this error is buried somewhere inside the winapi.inc file. Am I missing something?
Thanks

Carl -
I’ve dug through my Clarion books and references, thinking I may have once seem what might be the “EIP method” you’re referring to, but I can’t seems to locate it. Can you point me in the right direction?
Thanks again.

The error 3 is it cannot find the files so either their not in “appropriate folders” or your RED is not looking there, or had bad folders. Drop the files in your project folder to just get it to build.

@abrayshaw I gave you all the code you need in my reply. Did you get that to work?

In global Map declare the function. 

    Module('Windows')
            GetSystemMetrics(nIndex LONG),LONG,PASCAL,DLL(1)
    End

To call:

    MyScrollBarWidth = GetSystemMetrics(2)  !SM_CXVSCROLL equates to 2
1 Like

The zip file has the “missing” files in the libsrc folder. If you’re using a version higher than C6, then place those 2 files in your accessory\libsrc\win folder, or just in your app folder for testing.

Carl -
I did get the call to GetSystemMetrics to work. Thanks. But, as I said in an earlier post, it seems the value returned is the same whether or not the VSB is visible or not, so I can’t use it as I hoped.
Still trying! Thanks.