Hello All
Finally i was able to get the Multiline header listview working but its header is still blank despite that
it has allocated vertical space for the multilines
see the screen shot below
appreciate if someone can help me to get the header fill up, which i notice that in PB we use WSTRINGZ* 260
but there is no equivalent of WSTRINGZ* 260 in O2 ??
so without the WSTRINGZ* 260 , it cannot display the header
the listing and other files for this program is attached in the zip file
we are very close to resolving this problem, hope someone can help me here
Hi Chris,
glad to see you are making headway with this code.
ASCIIZ*260 szText
' WSTRING szText
wchar szText [260]
Thanxx Charles
i have replace the string szText with wchar [260] szText as shown below in the function ListView_SubclassProc ()
' ========================================================================================
' Processes messages for the subclassed ListView control.
FUNCTION ListView_SubclassProc ( _
BYVAL hWnd AS sys, _
BYVAL utMsg AS uint, _
BYVAL wParam AS sys, _
BYVAL lParam AS sys ) AS sys callback
' REQUIRED: Get the address of the original window procedure
sys pOldWndProc
pOldWndProc = GetProp(hWnd, "OLDWNDPROC")
SELECT CASE utMsg
CASE WM_DESTROY
' REQUIRED: Remove control subclassing
RemoveProp(hWnd, "OLDWNDPROC", GetWindowLongPtr(hWnd, GWLP_WNDPROC, @ListView_SubclassProc))
CASE WM_NOTIFY
NMHDR PTR pnmh
NMCUSTOMDRAW PTR pnmcd
' string szText
wchar [260] szText
' WSTRING szText
@pnmh = lParam
SELECT CASE pnmh.code
CASE NM_CUSTOMDRAW
@pnmcd = lParam
' Check the drawing stage
SELECT CASE pnmcd.dwDrawStage
' Prior to painting
CASE CDDS_PREPAINT
' Tell Windows we want individual notification
' of each item being drawn
FUNCTION = CDRF_NOTIFYITEMDRAW
EXIT FUNCTION
' Notification of each item being drawn
CASE CDDS_ITEMPREPAINT
sys hLvHeader
sys nIndex
sys nState
nIndex = pnmcd.dwItemSpec
nState = pnmcd.uItemState
' Get the header item text...
HD_ITEMA hdi
hdi.mask = HDI_TEXT
hdi.pszText = VARPTR(szText)
hdi.cchtextmax = SIZEOF(szText)
hLvHeader = ListView_GetHeader(hWnd)
Header_GetItemA(hLvHeader, nIndex, hdi)
' Create a new font
sys hFont
hFont = O2ApiCreateFont("Tahoma", 10, FW_BOLD)
' Select the font into the current devide context
sys hOldFont
hOldFont = SelectObject(pnmcd.hdc, hFont)
' Draw the button state...
IF (nState AND CDIS_SELECTED) THEN
DrawFrameControl pnmcd.hdc, pnmcd.rc, _
DFC_BUTTON, DFCS_BUTTONPUSH OR DFCS_PUSHED
ELSE
DrawFrameControl pnmcd.hdc, pnmcd.rc, _
DFC_BUTTON, DFCS_BUTTONPUSH
END IF
' Color the header background
sys hBrush
hBrush = CreateSolidBrush(RGB(243,250,5)) ' <------------ Change color
InflateRect pnmcd.rc, -2, -2
FillRect pnmcd.hdc, pnmcd.rc, hBrush
SetBkMode pnmcd.hdc, TRANSPARENT
' Color the header text
' SetTextColor pnmcd.hdc, RGB(40,45,215) ' <------------ Change color
SetTextColor pnmcd.hdc, RGB(0,0,215)
' Offset the text slightly if depressed...
IF (nState AND CDIS_SELECTED) THEN
InflateRect pnmcd.rc, -2, -2
END IF
' Draw multiline, using carriage returns (i.e. szText = "Customer" + CR + "number")
DrawText pnmcd.hdc, szText, LEN(szText), pnmcd.rc, DT_CENTER OR DT_VCENTER
' Cleanup
IF hBrush THEN
DeleteObject hBrush
END IF
IF hOldFont THEN
SelectObject pnmcd.hdc, hOldFont
END IF
IF hFont THEN
DeleteObject hFont
END IF
' Tell Windows the item has already been drawn
FUNCTION = CDRF_SKIPDEFAULT
EXIT FUNCTION
END SELECT
END SELECT
END SELECT
FUNCTION = CallWindowProc(pOldWndProc, hWnd, utMsg, wParam, lParam)
END FUNCTION
but the program just GPF
maybe at this point ??
hdi.pszText = VARPTR(szText)
this must be a pointer problem here bcos O2 will normally GPF when there is a pointer or
out of dimension array problems
Thanxx Charles
with
wchar szText [260]
it is still the same --> blank headers but don't GPF
need some tinkling on
hdi.pszText = VARPTR(szText)
You're returning a pointer to a local string. Make it global or static.
Thanxx Jose
i had changed sztext to global but still the headers are blank
Do you need a wchar or is it a char? The header specifies psztxt as asciiz ptr.
varptr is not needed but it resolves correctly
TYPE HD_ITEM
Mask AS uint ' UINT mask
cxy AS LONG ' int cxy
pszText AS ASCIIZ PTR ' LPSTR pszText
hbm AS sys ' HBITMAP hbm
cchTextMax AS LONG ' int cchTextMax
fmt AS LONG ' int fmt
lParam AS sys ' LPARAM lParam
iImage AS LONG ' int iImage // index of bitmap in ImageList
iOrder AS LONG ' int iOrder // where to draw this item
pvFilter AS sys ' void * pvFilter // [in] fillter data see above
state AS sys
END TYPE
i also tried using global char*260 szText but without success
'Header text
' wchar szText[260]
char*260 szText
try:
static char szText[260]
and remove the varptr
Thanxx Charles but this did not work
as you see i'm now using type HD_ITEMA instead of HD_ITEM
and Header_GetItemA() instead of Header_GetItem()
listing for ColorListView_MH.o2bas
'====================================================================
' Color Listview example modified Nov 4 2018
' which you can change fonts and color of text and background
' with Multi Line Header
'====================================================================
$ filename "ColorListView_MH.exe"
use rtl64
#lookahead
% review
uses dialogs
uses O2Common
'Identifier for ListView
#define IDC_LSV1 3801
' The program logo icon is obtained from the resource file
' the 400 must corespondence to the 400 in the rc file
#define IDI_LOGO 400
% ICON_BIG=1
% WM_SETICON=0x80
' control ID of statusbar
% IDC_Statusbar 420
macro ListView_InsertColumn(hwnd,iCol,pcol) (SendMessage(hwnd, LVM_INSERTCOLUMN, iCol, pcol))
macro ListView_SetColumnWidth(hwnd,iCol,cx) (SendMessage(hwnd, LVM_SETCOLUMNWIDTH, iCol, cx))
macro ListView_InsertItem(hwnd,pitem) (SendMessage(hwnd, LVM_INSERTITEM,0, pitem))
macro ListView_SetItem(hwnd,pitem) (SendMessage(hwnd, LVM_SETITEM,0, pitem))
% DS_CENTER=0x0800
% DS_MODALFRAME=0x80
% SS_CENTERIMAGE=0x200
% LVS_LIST 0x0003
% LVS_REPORT 0x0001
% LVS_EX_GRIDLINES 1
% LVS_EX_CHECKBOXES 4
% LVS_EX_FULLROWSELECT 0x0020
% LVS_SINGLESEL = 0x0004
% LVS_EX_DOUBLEBUFFER = 0x0010000
% LVSCW_AUTOSIZE -1
% LVSCW_AUTOSIZE_USEHEADER -2
' % LVM_INSERTCOLUMN=4123
' % LVM_SETCOLUMNWIDTH=4126
' % LVM_INSERTITEM=4103
' % LVM_SETITEM=4102
% LVCF_FMT 1
% LVCF_WIDTH 2
% LVCF_TEXT=4
% LVCF_SUBITEM 8
% LVCF_ORDER = 20
% LVIF_TEXT=1
% LVM_SETEXTENDEDLISTVIEWSTYLE 0x1036
% LVN_COLUMNCLICK = -108
% LVN_ITEMCHANGED = -101
% NM_CLICK -2
% LR_LOADFROMFILE=0x0010
% IMAGE_ICON=1
% STM_SETIMAGE=0x172
% SWP_NOZORDER=4
' Statusbar
% SB_SETPARTS 0x404
% SB_SETTEXT 0x401
% SBS_SIZEGRIP 16
% CCS_BOTTOM 3
' ListView messages
% LVM_FIRST = &H1000
% LVM_SETBKCOLOR = LVM_FIRST + 1
% LVM_SETTEXTCOLOR = LVM_FIRST + 36
% LVM_GETHEADER = LVM_FIRST + 31
% LVM_INSERTCOLUMN= LVM_FIRST + 27
% LVM_SETCOLUMNWIDTH=LVM_FIRST + 30
% LVM_INSERTITEM=%LVM_FIRST + 7
% LVM_SETITEM=LVM_FIRST + 6
% CLR_NONE = &HFFFFFFFF&
% GWLP_WNDPROC= -4
type LVCOLUMN
uint mask
int fmt
int cx
char* pszText
int cchTextMax
int iSubItem
int iImage
int iOrder
int cxMin
int cxDefault
int cxIdeal
end type
typedef LVCOLUMN LV_COLUMN
type LVITEM
uint mask
int iItem
int iSubItem
uint state
uint stateMask
char* pszText
int cchTextMax
int iImage // index of the list view item's icon
sys lParam // 32-bit value to associate with item
int iIndent
int iGroupId
uint cColumns
uint *puColumns
int *piColFmt
int iGroup
end type
typedef LVITEM LV_ITEM
type NMLISTVIEW
NMHDR hdr
int iItem
int iSubItem
uint uNewState
uint uOldState
uint uChanged
POINT ptAction
sys lParam
end type
typedef NMLISTVIEW NM_LISTVIEW
' Number of rows in the ListView
% NumRow = 200
' Number of columns in the ListView meaning 3 +1 = 4 columns
% NumCol = 3
! GetDlgItem lib "user32.dll" (sys hDlg, int nIDDlgItem) as sys
! IsDialogMessage lib "user32.dll" alias"IsDialogMessageA" (sys hDlg, sys lpMsg) as bool
! IsWindow lib "user32.dll" (sys hWnd) as bool
'Header text -- did NOT work
' wchar szText[260]
' char*260 szText
uses MultiLineHDO2
' Handle for the Main Dialog
sys hDlg
' Fonts handle
sys hFont
' Handle for the ListView
sys hListview
' Handle for status bar
sys hStatus
' Row and column number of current cell
Long CurrentCol, CurrentRow
'==========================================
' create and display the Listview
SUB DispListView
int i , j
string txtStr
LV_COLUMN lvc
LV_ITEM lvi
' Setup the fonts for the ListView
SendMessage(hListview,%WM_SETFONT,hFont,0)
' Subclass the ListView
SetProp hListView, "OLDWNDPROC", _
SetWindowLongPtr(hListView, GWLP_WNDPROC, @ListView_SubclassProc)
' Get the handle of the ListView header control and subclass it
sys hLvHeader
hLvHeader = ListView_GetHeader(hListView)
IF hLvHeader = 0 THEN
EXIT FUNCTION
end if
IF hLvHeader THEN
SetProp hLvHeader, "OLDWNDPROC", _
SetWindowLongPtr(hLvHeader, GWLP_WNDPROC, @LVHeader_SubclassProc)
END IF
'Setup the ListView Column Headers
' The first column must have a wider width to accomodate the checkbox
lvc.mask = LVCF_WIDTH or LVCF_ORDER
' Need to add some blanks behind the header string label
' inorder to get a wider column
txtStr="Column #" & str(1) + " " +cr
lvc.pszText = txtStr
lvc.iorder = 0
ListView_InsertColumn(hListview, 0, &lvc)
' All the other columns to have a narrower width
For i = 1 To NumCol
lvc.mask = LVCF_FMT OR LVCF_WIDTH OR LVCF_TEXT OR LVCF_SUBITEM
If i = NumCol then
' Leave the last column header blank as we are NOT putting data
' into this last column ( it act like a buffer )
txtStr = ""
Else
txtStr="Column #" & str(i+1) + cr + " level2 "
txtStr = Trim(txtStr)
End if
lvc.pszText = txtStr
lvc.iorder = i
ListView_InsertColumn(hListview, i, &lvc)
Next i
' Setup the Listview data Rows
For i=1 To NumRow
'First column
lvi.mask = LVIF_TEXT
txtStr = "Row #" & str(200-i+1) ", Col # 1"
lvi.pszText = txtStr
lvi.iSubItem = 0
ListView_InsertItem(hListview, &lvi)
'Remaining columns
for j=2 to NumCol
txtStr = "Row #" & str(200-i+1) ", Col # " & str(j)
lvi.pszText = txtStr
lvi.iSubItem = j-1
ListView_SetItem(hListview, &lvi)
next j
Next i
' Set the column widths according to width of each column header
for i = 0 to NumCol -1
ListView_SetColumnWidth(hListview,i,LVSCW_AUTOSIZE_USEHEADER)
next i
' make the last column a very narrow width as it is only a buffer column
' this would display as a double line
ListView_SetColumnWidth(hListview,NumCol,3)
' Place in the extended style for the listview
SendMessage(hListview, LVM_SETEXTENDEDLISTVIEWSTYLE, 0,
LVS_EX_FULLROWSELECT or LVS_EX_CHECKBOXES or LVS_EX_GRIDLINES )
' Shade those unused background portions of the main ListView to Alice Blue
' while the text color is Navy
SendMessage(hListView, LVM_SETTEXTCOLOR, 0,RGB(0,0,128))
SendMessage(hListView, LVM_SETBKCOLOR, 0,RGB(240,248,255))
END SUB
'====================================================================
' Main callback function
Function DlgProc( hDlg, uint uMsg, sys wParam, lParam ) as sys callback
' Obtain the handle for the ListView
hListview = GetDlgItem(hDlg, IDC_LSV1)
select case uMsg
case WM_INITDIALOG
' display the program icon
sys hInstance = GetModuleHandle(NULL)
sys hIcon = LoadIcon(hInstance, IDI_Logo)
'Set Icon to Main Window
SendMessage(hDlg, WM_SETICON, ICON_BIG, hIcon)
' Create and display the listview
DispListView
' status bar
CurrentRow = 1
CurrentCol = 1
UpdateStatusBar(hDlg)
case WM_COMMAND
select case loword(wParam)
case IDCANCEL
' exit
DeleteObject(hFont)
DestroyWindow( hDlg )
end select
case WM_NOTIFY
NMHDR pnm at lParam
if pnm.hwndFrom = hListview then
'ListView
NM_LISTVIEW LpLvNm at lParam
select case pnm.code
case LVN_COLUMNCLICK
CurrentCol = LpLvNm.iSubItem + 1
mbox "Header clicked at column " + str(CurrentCol)
case LVN_ITEMCHANGED
CASE NM_CLICK ' click on a cell
NM_LISTVIEW LpLvNm at (lParam)
CurrentRow = LpLvNm.iiTem + 1
CurrentCol = LpLvNm.iSubItem + 1
UpdateStatusBar(hDlg)
end select
end if
case WM_SIZE
RECT rcClient
// Calculate remaining height and size edit
GetClientRect(hDlg, &rcClient)
SetWindowPos(hListview, NULL, 0, rcClient.top, rcClient.right, rcClient.bottom, SWP_NOZORDER)
UpdateStatusBar(hDlg)
case WM_CLOSE
DestroyWindow( hDlg )
case WM_DESTROY
PostQuitMessage( null )
end select
return 0
end function
'=====================
' The status bar displaying the current position of cursor
' and help text for each column
SUB UpdateStatusBar(sys hWnd)
hStatus=GetDlgItem(hWnd, IDC_Statusbar)
SendMessage(hStatus, SB_SETTEXT, 0, "Row " & str(CurrentRow) & " : " & "Col " & str(CurrentCol))
' Help text for each column when a particular column is clicked
SELECT CASE CurrentCol
CASE 1
SendMessage(hStatus, SB_SETTEXT, 1, "Enter characters only")
CASE 2
SendMessage(hStatus, SB_SETTEXT, 1, "Enter numbers only")
CASE 3
SendMessage(hStatus, SB_SETTEXT, 1, "Enter Alphanumeric here")
END SELECT
END SUB
'====================================================================
' Display the Main Dialog
Function DispMainDialog
sys lpdt
MSG wMsg
dyn::init(lpdt)
Dialog( 1, 10,10,250,200, "Listview example 64bits ", lpdt,
WS_OVERLAPPEDWINDOW or DS_CENTER or WS_VISIBLE or WS_CLIPCHILDREN or WS_THICKFRAME,
8,"MS Sans Serif" )
' Add in the listview or WS_BORDER
CONTROL "",IDC_LSV1,"SysListView32", _
WS_VISIBLE or WS_TABSTOP or LVS_REPORT or LVS_SINGLESEL or LVS_EX_DOUBLEBUFFER , _
10,10,233,50, WS_EX_CLIENTEDGE
hFont = O2ApiCreateFont("Arial",9, FW_Bold)
hDlg = CreateModelessDialog( 0, @DlgProc, 0, lpdt )
hStatus = CreateStatusWindow(WS_CHILD | WS_BORDER | WS_VISIBLE | SBS_SIZEGRIP | CCS_BOTTOM, "", hDlg, IDC_Statusbar)
'Statusbar set parts
int statwidths[] = {100, -1}
SendMessage(hStatus, SB_SETPARTS, 2, &statwidths)
SendMessage(hStatus, SB_SETTEXT, 0, "Row : Col")
UpdateStatusBar(hDlg)
while GetMessage( @wMsg, null, 0, 0 ) <> 0
if IsDialogMessage( hDlg, @wMsg ) = 0 then
TranslateMessage( @wMsg )
DispatchMessage( @wMsg )
end if
wend
End Function
'------------------------------------
' Start of program
init_common_controls()
printl " at start LVM_GETHEADER " LVM_GETHEADER
DispMainDialog
listing for MultiLineHDO2.inc
' MultiLineHDO2.inc
' MultiLine Header routines for O2
' Updated : Nov 4 2018
Type WINDOWPOS
hwnd As sys
hWndInsertAfter As sys
x As Long
y As Long
cx As Long
cy As Long
flags As Long
End Type
' // Size = 8 bytes
TYPE HD_LAYOUT
RECT PTR prc ' RECT *prc
WINDOWPOS PTR pwpos ' WINDOWPOS *pwpos
END TYPE
TYPE NMCUSTOMDRAW
hdr AS NMHDR ' NMHDR hdr
dwDrawStage AS sys ' DWORD dwDrawStage
hdc AS sys ' HDC hdc
rc AS RECT ' RECT rc
dwItemSpec AS sys ' DWORD_PTR dwItemSpec // this is control specific, but it's how to specify an item. valid only with CDDS_ITEM bit set
uItemState AS uint ' UINT uItemState
lItemlParam AS sys ' LPARAM lItemlParam
END TYPE
TYPE HD_ITEM
Mask AS uint ' UINT mask
cxy AS LONG ' int cxy
pszText AS ASCIIZ PTR ' LPSTR pszText
hbm AS sys ' HBITMAP hbm
cchTextMax AS LONG ' int cchTextMax
fmt AS LONG ' int fmt
lParam AS sys ' LPARAM lParam
iImage AS LONG ' int iImage // index of bitmap in ImageList
iOrder AS LONG ' int iOrder // where to draw this item
pvFilter AS sys ' void * pvFilter // [in] fillter data see above
state AS sys
END TYPE
TYPE HD_ITEMA
Mask AS sys ' UINT mask
cxy AS LONG ' int cxy
pszText AS ASCIIZ PTR ' LPSTR pszText
hbm AS sys ' HBITMAP hbm
cchTextMax AS LONG ' int cchTextMax
fmt AS LONG ' int fmt
lParam AS sys ' LPARAM lParam
iImage AS LONG ' int iImage // index of bitmap in ImageList
iOrder AS LONG ' int iOrder // where to draw this item
pvFilter AS sys ' void * pvFilter // [in] fillter data see above
state AS sys
END TYPE
% SWP_FRAMECHANGED = &H20
% CDRF_NOTIFYITEMDRAW = &H20
% CDRF_SKIPDEFAULT = &H00000004
% HDI_TEXT = &H0002
% CDDS_PREPAINT = &H00000001
% CDDS_ITEM = &H00010000
% CDDS_ITEMPREPAINT = CDDS_ITEM OR CDDS_PREPAINT
% NM_FIRST = 0
% NM_CUSTOMDRAW = NM_FIRST - 12
% HDM_FIRST = &H1200
% HDM_LAYOUT = HDM_FIRST + 5
% HDM_GETITEMA = HDM_FIRST + 3
% HDM_GETITEMW = HDM_FIRST + 11
% DT_CENTER = &H00000001
% DT_VCENTER = &H00000004
'// itemState flags
% CDIS_SELECTED = &H0001
% DFC_BUTTON = 4
% DFCS_BUTTONPUSH = &H0010
% DFCS_PUSHED = &H00000200
' ========================================================================================
' Gets the handle to the header control used by a list-view control.
' ========================================================================================
FUNCTION ListView_GetHeader (BYVAL hwndLV AS sys) AS sys
FUNCTION = SendMessage(hwndLV, LVM_GETHEADER, 0, 0)
END FUNCTION
' ========================================================================================
FUNCTION Header_GetItemW (BYVAL hwndHD AS sys, BYVAL iItem AS sys, BYREF phdi AS HD_ITEM) AS sys
FUNCTION = SendMessageW( hwndHD, HDM_GETITEMW, iItem, VARPTR(phdi))
END FUNCTION
' ========================================================================================
' Gets information about an item in a header control.
' ========================================================================================
FUNCTION Header_GetItemA (BYVAL hwndHD AS sys, BYVAL iItem AS sys, BYREF phdi AS HD_ITEMA ) AS sys
FUNCTION = SendMessage(hwndHD, HDM_GETITEMA, iItem, VARPTR(phdi))
END FUNCTION
' ============================================================================
' Processes messages for the subclassed ListView header control.
FUNCTION LVHeader_SubclassProc( BYVAL hwnd AS sys , BYVAL usMsg AS uint ,
BYVAL wParam AS sys, BYVAL lParam AS sys ) AS sys callback
SELECT CASE usMsg
CASE WM_DESTROY
' REQUIRED: Remove control subclassing
SetWindowLongPtr hWnd, GWLP_WNDPROC, RemoveProp(hWnd, "OLDWNDPROC")
CASE %HDM_LAYOUT
' Fill the WINDOWPOS structure with
' the appropriate size and position of the
' header control and change the top position
' of the rectangle that the header
' control will occupy.
HD_LAYOUT phdl at (lparam)
phdl.pwpos.hwnd = hWnd
phdl.pwpos.flags = SWP_FRAMECHANGED
phdl.pwpos.x = phdl.prc.Left
phdl.pwpos.y = 0
phdl.pwpos.cx = phdl.prc.Right - phdl.prc.Left
phdl.pwpos.cy = 40 ' --> change me
phdl.prc.Top = 40 ' --> change me
FUNCTION = -1
EXIT FUNCTION
END SELECT
FUNCTION = CallWindowProc(GetProp(hWnd, "OLDWNDPROC"), hWnd, usMsg, wParam, lParam)
END FUNCTION
' ========================================================================================
' Processes messages for the subclassed ListView control.
FUNCTION ListView_SubclassProc ( _
BYVAL hWnd AS sys, _
BYVAL utMsg AS uint, _
BYVAL wParam AS sys, _
BYVAL lParam AS sys ) AS sys callback
' Header text
static char szText[260]
' REQUIRED: Get the address of the original window procedure
sys pOldWndProc
pOldWndProc = GetProp(hWnd, "OLDWNDPROC")
SELECT CASE utMsg
CASE WM_DESTROY
' REQUIRED: Remove control subclassing
RemoveProp(hWnd, "OLDWNDPROC", GetWindowLongPtr(hWnd, GWLP_WNDPROC, @ListView_SubclassProc))
CASE WM_NOTIFY
NMHDR PTR pnmh
NMCUSTOMDRAW PTR pnmcd
@pnmh = lParam
SELECT CASE pnmh.code
CASE NM_CUSTOMDRAW
@pnmcd = lParam
' Check the drawing stage
SELECT CASE pnmcd.dwDrawStage
' Prior to painting
CASE CDDS_PREPAINT
' Tell Windows we want individual notification
' of each item being drawn
FUNCTION = CDRF_NOTIFYITEMDRAW
EXIT FUNCTION
' Notification of each item being drawn
CASE CDDS_ITEMPREPAINT
sys hLvHeader
sys nIndex
sys nState
nIndex = pnmcd.dwItemSpec
nState = pnmcd.uItemState
' Get the header item text...
HD_ITEMA hdi
hdi.mask = HDI_TEXT
hdi.pszText = szText 'VARPTR(szText)
hdi.cchtextmax = SIZEOF(szText)
hLvHeader = ListView_GetHeader(hWnd)
Header_GetItemA(hLvHeader, nIndex, hdi)
' Create a new font
sys hFont
hFont = O2ApiCreateFont("Tahoma", 10, FW_BOLD)
' Select the font into the current devide context
sys hOldFont
hOldFont = SelectObject(pnmcd.hdc, hFont)
' Draw the button state...
IF (nState AND CDIS_SELECTED) THEN
DrawFrameControl pnmcd.hdc, pnmcd.rc, _
DFC_BUTTON, DFCS_BUTTONPUSH OR DFCS_PUSHED
ELSE
DrawFrameControl pnmcd.hdc, pnmcd.rc, _
DFC_BUTTON, DFCS_BUTTONPUSH
END IF
' Color the header background
sys hBrush
hBrush = CreateSolidBrush(RGB(243,250,5)) ' <------------ Change color
InflateRect pnmcd.rc, -2, -2
FillRect pnmcd.hdc, pnmcd.rc, hBrush
SetBkMode pnmcd.hdc, TRANSPARENT
' Color the header text
' SetTextColor pnmcd.hdc, RGB(40,45,215) ' <------------ Change color
SetTextColor pnmcd.hdc, RGB(0,0,215)
' Offset the text slightly if depressed...
IF (nState AND CDIS_SELECTED) THEN
InflateRect pnmcd.rc, -2, -2
END IF
' Draw multiline, using carriage returns (i.e. szText = "Customer" + CR + "number")
DrawText pnmcd.hdc, szText, LEN(szText), pnmcd.rc, DT_CENTER OR DT_VCENTER
' Cleanup
IF hBrush THEN
DeleteObject hBrush
END IF
IF hOldFont THEN
SelectObject pnmcd.hdc, hOldFont
END IF
IF hFont THEN
DeleteObject hFont
END IF
' Tell Windows the item has already been drawn
FUNCTION = CDRF_SKIPDEFAULT
EXIT FUNCTION
END SELECT
END SELECT
END SELECT
FUNCTION = CallWindowProc(pOldWndProc, hWnd, utMsg, wParam, lParam)
END FUNCTION
We had some problems with negative equates sign-extending into 64 bit. You could try forcing them to be dwords.
for instance:
% CLR_NONE = &HFFFFFFFF&
% GWLP_WNDPROC= -4
---->>
% CLR_NONE = dword &HFFFFFFFF
% GWLP_WNDPROC= dword -4
https://www.oxygenbasic.org/forum/index.php?topic=1592.msg17568#msg17568
when i use the dword fix
% CLR_NONE = dword &HFFFFFFFF
% GWLP_WNDPROC= dword -4
the result is still blank headers :-\