Is it possible to show more than one icon/button in an xBrowse cell ? (or can this be done only by gluing the columns ?)
Is it possible to show more than one icon/button in an xBrowse cell ? (or can this be done only by gluing the columns ?)
oCol:bDrawData := { | oCol, hDC, aRect |
local nLeft := aRect[1] local nTop := aRect[2]
// First icon DrawTransparent( hDC, hBmp1, nTop, nLeft )
// second icon DrawTransparent( hDC, hBmp2, nTop, nLeft + 20 )
return nil }
Hi, Silvio !
Did I understand correctly that when scrolling through xBrowse, oCol is performed for each row ?
oCol:bDrawData := { | oCol, hDC, aRect |nLeft := aRect[1], nTop := aRect[2], DrawTransparent( hDC, hBmp1, nTop, nLeft )}
You must ser the source xbrowse when insert + and - buttons tò have a samples
Maybe,
// Example Structure
WITH OBJECT oBrw:aCols[ nCol ]
:nEditType := EDIT_BUTTON
:aBtnBitmaps := { "btn_one", "btn_two" } // Two icons
:bBtnAction := { |nRow, nCol, nFlags, oCol| MyAction( oCol:nBtnClick ) }
END.or.
oCol:bPaintText := { |oCol, hDC, cText, oRect| ;
FW_DrawImage( hDC, "icon1", {oRect:nTop, oRect:nLeft, oRect:nBottom, oRect:nLeft+20} ),;
FW_DrawImage( hDC, "icon2", {oRect:nTop, oRect:nLeft+25, oRect:nBottom, oRect:nLeft+45} ),;
0 }.or.
WITH OBJECT oBrw:aCols[ nCol ]
:nEditType := EDIT_GET_BUTTON
:bEditBlock := { || ... }
ENDhttps://forums.fivetechsupport.com/viewtopic.php?p=225063#p225063
Regards, saludos.
Thanks, Karinha, I'll use it.
oCol:bDrawData is most suitable for my purposes, but I did not find such a block of code in xBrowse. :?:
Natter wrote:Thanks, Karinha, I'll use it.
oCol:bDrawData is most suitable for my purposes, but I did not find such a block of code in xBrowse. :?:
Maybe,
// Exemplo: Desenhando um texto colorido baseado no valor da célula
oCol:bDrawData := { | oCol, xValue, nRow, nCol, nWidth, nHeight | ;
DrawCellData( oCol, xValue, nRow, nCol, nWidth, nHeight ) }
// Função auxiliar para o desenho personalizado
STATIC FUNCTION DrawCellData( oCol, xValue, nRow, nCol, nWidth, nHeight )
local oBrw := oCol:oBrw
local nClrText := CLR_BLACK
// Logica: Se o valor for negativo, texto vermelho
IF ValType( xValue ) == "N" .and. xValue < 0
nClrText := CLR_RED
ENDIF
// Desenha o texto formatado na célula
oCol:DrawText( xValue, nRow, nCol, nWidth, nHeight, nClrText, nil, nil )
RETURN nilhttps://fivetechsoft.com/forums/viewtopic.php?t=12654
Regards, saludos.
oCol:bDrawData := { | oCol, xData, lInvert, oBrush, lSelected | ;
DrawCustomCell( oCol, xData, lInvert, ... ) }#include "FiveWin.ch"
#include "XBrowse.ch"
function Main()
local oDlg, oBrw, oCol
local aData := { {"João", "joao@email.com"}, {"Maria", "maria@email.com"} }
DEFINE DIALOG oDlg SIZE 400, 300
@ 0, 0 XBROWSE oBrw OF oDlg ARRAY aData AUTOCOLS
// Vamos personalizar a primeira coluna
oCol := oBrw:aCols[1]
oCol:cHeader := "Contatos"
// Define a altura da linha maior para caber os dados
oBrw:nDataLines := 2
// Custom Drawing
oCol:bDrawData := { | oCol, xData, lInvert, oBrush, lSelected | ;
DrawCustomCell( oCol, oBrw, lInvert ) }
oBrw:CreateFromCode()
ACTIVATE DIALOG oDlg CENTERED
return nil
// Função que realiza o desenho customizado
static function DrawCustomCell( oCol, oBrw, lInvert )
local oGraphics := oCol:oBrw:oGraphics // GDI+
local nRow := oCol:oBrw:nRowSel
local nCol := oCol:nDisplayCol
local nWidth := oCol:nWidth
local nHeight := oCol:nHeight
local hDC := oCol:oBrw:hDC
local aRowData := oBrw:aRow // Dados da linha atual
// 1. Limpar fundo (opcional, mas recomendado)
FillRect( hDC, {oBrw:nRowSel, oCol:nDisplayCol, oBrw:nRowSel + oBrw:nRowHeight, oCol:nDisplayCol + oCol:nWidth }, GetSysColor( COLOR_WINDOW ) )
// 2. Desenhar primeira linha (Nome - Negrito)
SetTextColor( hDC, CLR_BLUE )
DrawText( hDC, aRowData[1], {oBrw:nRowSel + 2, oCol:nDisplayCol + 2, oBrw:nRowSel + (oBrw:nRowHeight/2), oCol:nDisplayCol + nWidth}, 0 )
// 3. Desenhar segunda linha (Email - Cinza/Menor)
SetTextColor( hDC, CLR_GRAY )
DrawText( hDC, aRowData[2], {oBrw:nRowSel + (oBrw:nRowHeight/2), oCol:nDisplayCol + 2, oBrw:nRowSel + oBrw:nRowHeight, oCol:nDisplayCol + nWidth}, 0 )
return nilI hope this helps you.
Regards, saludos.
Is it possible to place more than 2 buttons/pictures in an xBrowse cell?
Dear Yuri,
#include "FiveWin.ch"
#include "XBrowse.ch"
static hBmp1, hBmp2, hBmp3
function Main()
local oDlg, oBrw, oFont, oFontSmall
local aData := { {"João", "joao@email.com"}, ;
{"Maria", "maria@email.com"}, ;
{"Pedro", "pedro@email.com"} }
// Load bitmaps (16x16 icons)
hBmp1 := ReadBitmap( 0, "..\bitmaps\16x16\adddbf.bmp" )
hBmp2 := ReadBitmap( 0, "..\bitmaps\16x16\zoom2.bmp" )
hBmp3 := ReadBitmap( 0, "..\bitmaps\16x16\delete.bmp" )
DEFINE FONT oFont NAME "Segoe UI" SIZE 0, -14
DEFINE FONT oFontSmall NAME "Segoe UI" SIZE 0, -11
DEFINE DIALOG oDlg SIZE 500, 400 TITLE "Custom Cell Drawing" FONT oFont
@ 0, 0 XBROWSE oBrw OF oDlg ;
ARRAY aData COLUMNS 1 ;
HEADERS "Contatos" ;
COLSIZES 400 ;
CELL NOBORDER
WITH OBJECT oBrw
:nRowHeight := 50
:nStretchCol := 1
:lRecordSelector := .F.
:CreateFromCode()
:aCols[ 1 ]:bPaintText := { | oCol, hDC, cText, aCoors, aColors, lHighlight | ;
DrawCustomCell( oCol, hDC, cText, aCoors, aColors, lHighlight, oFontSmall ) }
END
oBrw:SetFocus()
ACTIVATE DIALOG oDlg CENTERED ;
ON INIT oBrw:SetFocus()
// Cleanup
DeleteObject( hBmp1 )
DeleteObject( hBmp2 )
DeleteObject( hBmp3 )
oFont:End()
oFontSmall:End()
return nil
//----------------------------------------------------------------------------//
static function DrawCustomCell( oCol, hDC, cText, aCoors, aColors, lHighlight, oFontSmall )
// aCoors = { nTop, nLeft, nBottom, nRight }
local nTop := aCoors[ 1 ]
local nLeft := aCoors[ 2 ]
local nBottom := aCoors[ 3 ]
local nRight := aCoors[ 4 ]
local aRow := oCol:oBrw:aRow
local nMidY := nTop + Int( ( nBottom - nTop ) / 2 )
local nIconY := nTop + Int( ( nBottom - nTop - 16 ) / 2 ) // vertically center 16px icons
local hOldFont
// 1. Draw Name (first line, bold)
SetTextColor( hDC, CLR_BLACK )
DrawTextEx( hDC, aRow[ 1 ], { nTop + 2, nLeft + 2, nMidY, nRight - 60 }, DT_LEFT + DT_VCENTER + DT_SINGLELINE )
// 2. Draw Email (second line, smaller font, gray)
SetTextColor( hDC, CLR_HGRAY )
hOldFont := SelectObject( hDC, oFontSmall:hFont )
DrawTextEx( hDC, aRow[ 2 ], { nMidY, nLeft + 2, nBottom - 2, nRight - 60 }, DT_LEFT + DT_VCENTER + DT_SINGLELINE )
SelectObject( hDC, hOldFont )
// 3. Draw 3 icons on the right side, vertically centered
PalBmpDraw( hDC, nIconY, nRight - 54, hBmp1 ) // icon 1
PalBmpDraw( hDC, nIconY, nRight - 36, hBmp2 ) // icon 2
PalBmpDraw( hDC, nIconY, nRight - 18, hBmp3 ) // icon 3
return nilAntonio,YES, that's what you need !!!
Is it possible to:
Yes, all three are possible. Here's the complete code:
Simply use a variable
local nIconSize := 16 // icon width in pixels
local nGap := 10 // distance between icons (change this value)
PalBmpDraw( hDC, nIconY, nX, hBmp1 )
PalBmpDraw( hDC, nIconY, nX + nIconSize + nGap, hBmp2 )
PalBmpDraw( hDC, nIconY, nX + 2*(nIconSize + nGap), hBmp3 )Calculate the total width of all icons + gaps, then offset from the cell center:
local nTotalWidth := (nIcons * nIconSize) + ((nIcons - 1) * nGap)
local nStartX := nLeft + Int( (nCellWidth - nTotalWidth) / 2 )Use
For double-click, use
#include "FiveWin.ch"
#include "XBrowse.ch"
static hBmp1, hBmp2, hBmp3
static nIconSize := 16
static nGap := 10 // << change this to adjust distance between icons
static nIcons := 3
function Main()
local oDlg, oBrw, oFont, oFontSmall
local aData := { {"João", "joao@email.com"}, ;
{"Maria", "maria@email.com"}, ;
{"Pedro", "pedro@email.com"} }
hBmp1 := ReadBitmap( 0, "..\bitmaps\16x16\adddbf.bmp" )
hBmp2 := ReadBitmap( 0, "..\bitmaps\16x16\zoom2.bmp" )
hBmp3 := ReadBitmap( 0, "..\bitmaps\16x16\delete.bmp" )
DEFINE FONT oFont NAME "Segoe UI" SIZE 0, -14
DEFINE FONT oFontSmall NAME "Segoe UI" SIZE 0, -11
DEFINE DIALOG oDlg SIZE 500, 400 TITLE "Custom Cell Icons" FONT oFont
@ 0, 0 XBROWSE oBrw OF oDlg ;
ARRAY aData COLUMNS 1 ;
HEADERS "Contatos" ;
COLSIZES 400 ;
CELL NOBORDER
WITH OBJECT oBrw
:nRowHeight := 50
:nStretchCol := 1
:lRecordSelector := .F.
// Custom painting
:aCols[ 1 ]:bPaintText := { | oCol, hDC, cText, aCoors, aColors, lHighlight | ;
DrawCustomCell( oCol, hDC, aCoors, oFontSmall ) }
// Single-click detection on icons
:bLClicked := { |nRow, nCol, nFlags, oBrw| ;
CheckIconClick( nRow, nCol, oBrw ) }
:CreateFromCode()
END
oBrw:SetFocus()
ACTIVATE DIALOG oDlg CENTERED
DeleteObject( hBmp1 )
DeleteObject( hBmp2 )
DeleteObject( hBmp3 )
oFont:End()
oFontSmall:End()
return nil
//----------------------------------------------------------------------------//
static function DrawCustomCell( oCol, hDC, aCoors, oFontSmall )
local nTop := aCoors[ 1 ]
local nLeft := aCoors[ 2 ]
local nBottom := aCoors[ 3 ]
local nRight := aCoors[ 4 ]
local aRow := oCol:oBrw:aRow
local nMidY := nTop + Int( ( nBottom - nTop ) / 2 )
local nCellWidth := nRight - nLeft
local hOldFont
// -- Total width of all icons + gaps --
local nTotalWidth := ( nIcons * nIconSize ) + ( ( nIcons - 1 ) * nGap )
// -- Center icons horizontally --
local nStartX := nLeft + Int( ( nCellWidth - nTotalWidth ) / 2 )
// -- Vertically center icons in top half --
local nIconY := nTop + Int( ( nMidY - nTop - nIconSize ) / 2 )
// 1. Draw 3 icons centered horizontally with configurable gap
PalBmpDraw( hDC, nIconY, nStartX, hBmp1 )
PalBmpDraw( hDC, nIconY, nStartX + nIconSize + nGap, hBmp2 )
PalBmpDraw( hDC, nIconY, nStartX + 2 * ( nIconSize + nGap ), hBmp3 )
// 2. Draw Name below icons (centered)
SetTextColor( hDC, CLR_BLACK )
DrawTextEx( hDC, aRow[ 1 ], { nMidY, nLeft, nMidY + 14, nRight }, ;
DT_CENTER + DT_SINGLELINE + DT_VCENTER )
// 3. Draw Email below name (centered, smaller, gray)
SetTextColor( hDC, CLR_HGRAY )
hOldFont := SelectObject( hDC, oFontSmall:hFont )
DrawTextEx( hDC, aRow[ 2 ], { nMidY + 14, nLeft, nBottom - 2, nRight }, ;
DT_CENTER + DT_SINGLELINE + DT_VCENTER )
SelectObject( hDC, hOldFont )
return nil
//----------------------------------------------------------------------------//
static function CheckIconClick( nRow, nCol, oBrw )
local oCol := oBrw:aCols[ 1 ]
local nLeft := oCol:nDisplayCol
local nRight := nLeft + oCol:nWidth
local nCellWidth := nRight - nLeft
local nTotalWidth := ( nIcons * nIconSize ) + ( ( nIcons - 1 ) * nGap )
local nStartX := nLeft + Int( ( nCellWidth - nTotalWidth ) / 2 )
local nIcon1Left, nIcon2Left, nIcon3Left
// Only process if click is in the data area (not header)
if oBrw:MouseRowPos( nRow ) <= 0
return nil
endif
// Calculate each icon's horizontal range
nIcon1Left := nStartX
nIcon2Left := nStartX + nIconSize + nGap
nIcon3Left := nStartX + 2 * ( nIconSize + nGap )
do case
case nCol >= nIcon1Left .and. nCol <= nIcon1Left + nIconSize
MsgInfo( "Icon 1 clicked! Row: " + oBrw:aRow[ 1 ], "Add" )
case nCol >= nIcon2Left .and. nCol <= nIcon2Left + nIconSize
MsgInfo( "Icon 2 clicked! Row: " + oBrw:aRow[ 1 ], "Zoom" )
case nCol >= nIcon3Left .and. nCol <= nIcon3Left + nIconSize
MsgInfo( "Icon 3 clicked! Row: " + oBrw:aRow[ 1 ], "Delete" )
endcase
return nilCentering is done by computing
Click detection uses
For double-click instead of single-click, use
You can also add vertical hit-testing by checking
This option involves drawing an icon from a file.
hBmp1 := ReadBitmap( 0, "..\bitmaps\16x16\adddbf.bmp"
PalBmpDraw( hDC, nIconY, nStartX, hBmp1 )How can I draw an icon from a resource?
hBmp1 := LoadBitmap( GetResources(), cResName )Thanks, Enrico!