Aqui usando o browse com objeto Record Set, e ainda com ordenação variável por coluna.
Código: Selecionar todos
/*
\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\
\ Empresa.: SIMPLES - SISTEMAS INFORMATIZADOS
\ Programa: SCP_Procedure .PRG
\ Data....: 15-02-05
\ Sistema.: SISTEMA DE CONTABILIDADE PéBLICA - Scp21H
\ Funcao..: Rotinas auxiliares
\ Analista: CLODOALDO MONTEIRO
\ Criacao.: GAS-Pro v4.0o
\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\
https://pctoledo.org/forum/viewtopic.php?f=4&t=23743
*/
#pragma -w0
#pragma -es0
#include "GAS.CH" // inicializa constantes manifestas
//#include "FileIO.CH"
#include "TBrowse.ch"
#include "inkey.ch"
Procedure REG_BrowseCtrlZ_RS( cCodigo, cAlias )
Local mAlias := Alias(), mTotal, mFiltro, msg, mCodigo
Local mSQL, oRs, oTBrowse, telaSave, co_r, mJanela := 0
Private cod_sos, cur_sor, ccAlias
ccAlias := If( Empty( cAlias), Alias(), cAlias )
mCodigo := cCodigo
IF nivelop < 3 // se userName nao autorizado,
Return // cai fora..
EndIf
Set Key K_CTRL_Z TO
cur_sor := SetCursor(0) // salva cursor/acende
cod_sos := 1
Begin Sequence
mSQL := "SELECT * "
mSQL += " FROM Reg"
mSQL += " Where inStr( '" + ccAlias + "', reg_alias ) <> 0"
If !Empty( cCodigo)
mSQL += " AND reg_codigo Like '" + cCodigo + "%'"
EndIf
mSQL += " Order By reg_data Desc, reg_hora Desc;"
oRs := DbfSQLRsOpen(oCnDbf, mSQL)
WITH OBJECT oRs
If :RecordCount() = 0
MsgAtencao( "Nada a consultar para esta tabela" )
Break
EndIf
oTBrowse := { ;
{ " # " , { || oRs:AbsolutePosition() }, '@E 999,999', 7 },;
{ "Data" , { || Transform(oRs:Fields( "reg_data" ):Value, '@D') }, '', 10 },;
{ "Hora" , { || oRs:Fields( "reg_hora" ):Value }, '', 08 },;
{ "Competˆncia" , { || oRs:Fields( "reg_compet" ):Value }, '@R 9999/99', 08 },;
{ "Usu rio" , { || HB_AnsiToOem( oRs:Fields( "reg_usuari" ):Value ) }, '', 20 },;
{ "Tabela" , { || oRs:Fields( "reg_alias" ):Value }, '', 10 },;
{ "Acesso C¢digo" , { || oRs:Fields( "reg_codigo" ):Value }, '', 20 },;
{ "Tipo de movimento" , { || HB_AnsiToOem( oRs:Fields( "reg_tipo" ):Value ) }, '', 12 },;
{ "Campo/Chave" , { || oRs:Fields( "reg_campo" ):Value }, '', 20 },;
{ "Descri‡Æo / Campo chave" , { || HB_AnsiToOem( oRs:Fields( "reg_titulo" ):Value ) }, '', 30 },;
{ "Conte£do anterior / Mensagem 1", { || HB_AnsiToOem( oRs:Fields( "reg_antes" ):Value ) }, '', 50 },;
{ "Conte£do atual / Mensagem 2" , { || HB_AnsiToOem( oRs:Fields( "reg_depois" ):Value ) }, '', 50 },;
{ "IP" , { || oRs:Fields( "reg_ip" ):Value }, '', 15 },;
{ "Net Name" , { || HB_AnsiToOem( oRs:Fields( "reg_NetNam" ):Value ) }, '', 20 },;
{ "S.O. VersÆo" , { || HB_AnsiToOem( oRs:Fields( "reg_SOVers" ):Value ) }, '', 30 },;
{ "S.O. Usu rio" , { || HB_AnsiToOem( oRs:Fields( "reg_SOuser" ):Value ) }, '', 30 },;
{ "MAC Rede" , { || oRs:Fields( "reg_mac" ):Value }, '', 20 },;
{ "Flag" , { || oRs:Fields( "flag" ):Value }, '', 15 };
}
BrowseADORS( 2, 1, p_nNormalMaxRow -1, p_nNormalMaxCol -1, oRs, oTBrowse, cAlias, cCodigo )
END WITH
oRs:Close()
oRs := NIL
End Sequence
Set Key K_CTRL_Z TO VE_CRUD( )
SetCursor(cur_sor) // restabelece o cursor
FreeMemory()
Return
FUNCTION BrowseADORS( nTop, nLeft, nBottom, nRight, oRs, oTBrowse, cTabela, cFiltro, cFilterKey, bKeyboard, bUserFunction, nFixToCol, aADOFilterList, lKeyboard )
LOCAL oBrowse
LOCAL lContinue := .T. ,;
nKeyPressed := 0,;
nArryRowNo := 1,;
i, bBlock, oTBColumn, oCol, xVar, mVar
Local co_r
(aADOFilterList)
(cFilterKey)
Default( @lKeyboard, .T. )
If AbreJanela( 'VISUALIZAÇÃO DOS LOGS DA TABELA: ' + cTabela, nTop, nLeft, nBottom, nRight, ) == 0
MsgError( "Erro ao abrir Janela de dados." )
Return
EndIf
co_r := SetColor( drvcortel )
Caixa(mold, nTop, nLeft, nBottom, nRight)
oBrowse := TBrowseNew( nTop + 1, nLeft, nBottom -1, nRight )
oBrowse:colorspec := drvcorbox + ", " + drvcorhlp + ", " + drvcorenf + ", " + drvcorGet + ", " + INVCOR(drvcorpad)
oBrowse:headsep := chr(205) + chr(203) + chr(205) // separador do cabecalho (Í-Í)
oBrowse:colsep := " " + chr(179) + " " // separador das colunas ( ³ )
oBrowse:footSep := chr(205) + chr(202) + chr(205) // separador do cabecalho (Í-Í)
@ oBrowse:ntop-1, oBrowse:nleft Say '[Filtro: ' + cFiltro + ']' Color corcampo
@ oBrowse:ntop-1, oBrowse:nRight -13 Say '[Qtd: ' + Transform(oRs:RecordCount(), '@E 999,999]') Color corcampo
@ oBrowse:nBottom + 1, oBrowse:nleft + 1 Say 'Tecle as [setas] para movimentar ou [ESC] para sair.'
oBrowse:GoTopBlock := { || oRs:MoveFirst() }
oBrowse:GoBottomBlock := { || oRs:MoveLast() }
oBrowse:SkipBlock := { | n | oRsBrowseSkipper( oRs, n ) }
IF nFixToCol <> NIL
oBrowse:freeze := nFixToCol
EndIf
For i := 1 To Len(oTBrowse)
oTBColumn := TBColumn():New( oTBrowse[i, 1], oTBrowse[i, 2] )
oTBColumn:Picture := oTBrowse[ i, 3 ]
oTBColumn:Width := oTBrowse[ i, 4 ]
oBrowse:AddColumn( oTBColumn )
oBrowse:getcolumn(i):cargo := 0
Next
While lContinue // Browse's loop
IF NextKey() = 0
oBrowse:RefreshCurrent()
While .not. oBrowse:stabilize()
EndDo // Stabilizing loop
oBrowse:ColorRect( { oBrowse:RowPos, oBrowse:LeftVisible, oBrowse:RowPos, oBrowse:RightVisible }, { 5, 5 } ) // linha está com o cursor
oBrowse:ColorRect( { oBrowse:RowPos, oBrowse:ColPos, oBrowse:RowPos, oBrowse:ColPos }, { 2, 2 } ) // linha/coluna está com o cursor
IF ! Empty( oBrowse:Freeze ) // Marcar parte congelada
oBrowse:ColorRect( { oBrowse:RowPos, 1, oBrowse:RowPos, oBrowse:Freeze }, { 5, 5 } )
EndIf
wvw_DrawFocusRect(, oBrowse:RowPos + nTop + 2, oBrowse:nLeft, oBrowse:RowPos + nTop + 2, oBrowse:nRight ) // linha está com o cursor
EndIf
nKeyPressed := KeyPressed( @oBrowse )
If nKeyPressed == K_CTRL_O
nCol := oBrowse:colPos
mNomeCol := oTBrowse[nCol, 1]
For i := 1 To Len(oTBrowse)
oBrowse:getColumn( i ):heading := oTBrowse[i, 1]
Next
If nCol > 1
cField := oRs:Fields(nCol -1):Name
oCol := oBrowse:getColumn(nCol)
mDescend := ''
If oBrowse:getColumn( nCol ):cargo = 0
mDescend := ''
oCol:heading := PadR(oTBrowse[nCol, 1], oTBrowse[ nCol, 4 ] -2) + ' ' + Chr(26)
oBrowse:getColumn( nCol ):cargo := 1
ElseIf oBrowse:getColumn( nCol ):cargo = 1
mDescend := ' DESC'
oCol:heading := PadR(oTBrowse[nCol, 1], oTBrowse[ nCol, 4 ] -2) + ' ' + Chr(27)
oBrowse:getColumn( nCol ):cargo := 2
ElseIf oBrowse:getColumn( nCol ):cargo = 1
mDescend := ''
oCol:heading := PadR(oTBrowse[nCol, 1], oTBrowse[ nCol, 4 ] -2) + ' ' + Chr(26)
oBrowse:getColumn( nCol ):cargo := 1
Endif
oRs:Sort := cField + mDescend
oRs:MoveFirst()
oBrowse:configure()
mDescri := 'Ordem: ' + mNomeCol + ' -> ('+cField+')'
@ oBrowse:nBottom + 1, oBrowse:nRight - Len(mDescri) -1 Say mDescri Color drvCorHlp
Endif
Endif
lContinue := TBrApplyKey( oBrowse, nKeyPressed )
IF nKeyPressed = 0 // nao teclou nada, sai pelo
oBrowse:refreshall() // tempo de "refresh" entao
LOOP // na tela e volta
EndIf
EndDo
SetPos( p_nNormalMaxCol -1, 0 )
FechaJanela()
SetColor( co_r )
RETURN Nil
Static FUNCTION TBrApplyKey( oBrowse, nKey )
LOCAL lRVal := .T., mVar, i
DO CASE
CASE nKey == K_UP
oBrowse:Up()
CASE nKey == K_LEFT
oBrowse:Left()
CASE nKey == K_RIGHT
oBrowse:Right()
CASE nKey == K_DOWN
oBrowse:down()
CASE nKey == K_HOME
oBrowse:home()
CASE nKey == K_END
oBrowse:end()
CASE nKey == K_PGUP
oBrowse:pageUp()
CASE nKey == K_PGDN
oBrowse:pageDown()
CASE nKey == K_CTRL_PGDN
oBrowse:goBottom()
CASE nKey == K_CTRL_PGUP
oBrowse:goTop()
CASE nKey == K_CTRL_HOME
oBrowse:panHome()
CASE nKey == K_CTRL_END
oBrowse:panEnd()
CASE nKey == K_ESC
lRVal := .F.
ENDCASE
RETURN lRVal // TBrApplyKey()
STATIC FUNCTION oRsBrowseSkipper( oRs, nSkip )
LOCAL nRec := oRs:AbsolutePosition()
IF ! oRs:Eof()
oRs:Move( nSkip )
IF oRs:Eof()
oRs:MoveLast()
EndIf
IF oRs:Bof()
oRs:MoveFirst()
EndIf
EndIf
RETURN oRs:AbsolutePosition() - nRec
/*
IF ( bAction := SetKey( nKey ) ) <> NIL
EVal( bAction, ProcName(), ProcLine(), ReadVar() )
EndIf
//nMRow := MRow()
//nMCol := MCol()
DO CASE
CASE nKey > 999
//DO CASE
//CASE mBrzMove( oBrowse, nMRow, nMCol, nTop + 1, nLeft + 1, nBottom - 1, nRight - 1 )
//CASE mBrzClick( oBrowse, nMRow, nMCol )
// nKey := 0
// KEYBOARD Chr( K_ENTER )
// LOOP
//ENDCASE
CASE nKey == K_ENTER .and. bUserFunction == NIL
Do While ! oBrowse:Stable
oBrowse:Stabilize()
EndDo
IF bKeyboard <> NIL
IF Valtype( EVal( bKeyboard ) ) == "N"
//Errorsys_WriteErrorLog( "KEYBOARD numérico no BROWSEADO", 2 )
cKeyboard := LTrim( Str( EVal( bKeyBoard ), 16, 0 ) ) + Chr( K_ENTER )
IF lKeyBoard
KEYBOARD cKeyBoard
EndIf
Else
cKeyboard := EVal( bKeyBoard ) + Chr( K_ENTER )
IF lKeyboard
KEYBOARD cKeyboard
EndIf
EndIf
EndIf
EXIT
CASE nkey == K_CTRL_PGDN ; nKey := 0; oBrowse:GoBottom() ; LOOP
CASE nkey == K_CTRL_PGUP ; nKey := 0; oBrowse:GoTop() ; LOOP
CASE nkey == K_DOWN ; nKey := 0; oBrowse:Down() ; LOOP
CASE nkey == K_HOME ; nKey := 0; oBrowse:GoTop() ; LOOP
CASE nkey == K_END ; nKey := 0; oBrowse:GoBottom() ; LOOP
CASE nkey == K_LEFT ; nKey := 0; oBrowse:Left() ; LOOP
CASE nkey == K_RIGHT ; nKey := 0; oBrowse:Right() ; LOOP
CASE nkey == K_PGDN ; nKey := 0; oBrowse:PageDown() ; LOOP
CASE nkey == K_PGUP ; nKey := 0; oBrowse:PageUp() ; LOOP
CASE nkey == K_UP ; nKey := 0; oBrowse:Up() ; LOOP
CASE nKey == K_ESC ; EXIT
CASE nKey == K_ALT_F
CASE nKey == K_BS
//CASE IsRange( nKey, 32, 127 ) .and. cFilterKey <> NIL .and. ! cnSQL:Eof()
ENDCASE
IF bUserFunction <> NIL
Do While ! oBrowse:Stable
oBrowse:Stabilize()
EndDo
SET CURSOR ON
EVal( bUserFunction, oBrowse, nKey, cnSQL )
oBrowse:RefreshAll()
EndIf
nKey := 0 // para refresh
EndDo
FechaJanela()
SetColor( co_r )
RETURN cKeyboard
*/