Browse com ADO

Aqui você poderá oferecer suas Contribuições, Dicas e Tutoriais (Texto ou Vídeo) que sejam de interesse de todos.

Moderador: Moderadores

Avatar do usuário
JoséQuintas
Administrador
Administrador
Mensagens: 20267
Registrado em: 26 Fev 2007 11:59
Localização: São Paulo-SP

Browse com ADO

Mensagem por JoséQuintas »

A origem é deste post, do Alexandre Santos (AlxSts)

https://pctoledo.org/forum/viewto ... sql+server

Como está na resposta de outra coisa, talvez fique difícil de ser localizado o browse para ADO.
Aqui fiz algumas mudanças.
É um browse simples, sem qualquer tipo de filtro ou opção especial.
Só usar um browse de DBFs como referência, e adicionar recursos.

Para o recordset, usei o nome de oTemporario, fica claro pra quem não usa ADO, o que ele representa.

Código: Selecionar todos

#include "tbrowse.ch"

PROCEDURE Main

 LOCAL oConexao, oTemporario, oTBrowse

 oConexao := ConexaoMySql()
 oConexao:Open()
 oTemporario := oConexao:Execute( "SELECT CODIGO, NOME, ENDERECO FROM CLIENTES ORDER BY NOME" )
 oTBrowse := { ;
   { "CODIGO", { || Pad( oTemporario:Fields( "CODIGO" ):Value, 10 ) } }, ;
   { "NOME",  { || Pad( oTemporario:Fields( "NOME" ):Value, 30 ) } }, ;
   { "ENDERECO", { || Pad( oTemporario:Fields( "ENDERECO" ):Value, 30 ) } } }
 BrowseADO( oTemporario, oTBrowse )

 oTemporario:Close()
 oConexao:Close()
 RETURN

FUNCTION BrowseADO( oTemporario, oTBrowse )

 LOCAL oBrowse, nKey, oElement

 oBrowse := TBrowseDB():new( 04, 3, MaxRow() - 7, MaxCol() - 3 )

 oBrowse:goTopBlock  := { || oTemporario:moveFirst() }
 oBrowse:goBottomBlock := { || oTemporario:moveLast() }
 oBrowse:skipBlock  := { | n | ADOSkipper( oTemporario, n ) }

 FOR EACH oElement IN oTBrowse
   oBrowse:AddColumn( TBColumnNew( oElement[ 1 ], oElement[ 2 ] ) )
 NEXT

 DO WHILE .T.
   oBrowse:forceStable()
   oBrowse:ColorRect( { oBrowse:RowPos, oBrowse:LeftVisible, oBrowse:RowPos, oBrowse:RightVisible }, { 2, 1 } )
   oBrowse:ColorRect( { oBrowse:RowPos, oBrowse:ColPos, oBrowse:RowPos, oBrowse:ColPos }, { 3, 2 } )
   oBrowse:refreshCurrent()
   nKey := Inkey(0)
   DO CASE
   CASE oBrowse:ApplyKey( nKey ) == TBR_EXIT
    EXIT
   ENDCASE
 ENDDO

 RETURN NIL

STATIC FUNCTION ADOSkipper( oTemporario, nSkip )

 LOCAL nRec := oTemporario:AbsolutePosition

 IF ! ( oTemporario:Eof )
   oTemporario:Move( nSkip )
   IF oTemporario:Eof
    oTemporario:moveLast()
   ENDIF
   IF oTemporario:Bof
    oTemporario:moveFirst()
   ENDIF
 ENDIF

 RETURN oTemporario:AbsolutePosition - nRec

FUNCTION ConexaoMySql()

 LOCAL oConexao := win_OleCreateObject( "ADODB.Connection" )

 oConexao:ConnectionString := "colocar_a_string"
 oConexao:CursorLocation := 3 // adUseClient
 oConexao:CommandTimeOut := 600
 oConexao:ConnectionTimeOut := 600
 RETURN oConexao
Provavelmente vão querer adicionar opções de:
codeblock a executar, filtrar colunas, cores no tbrowse, navegação por mouse, filtro enquanto digita, etc, mas de um modo geral isso pode ser encontrado em qualquer browse de DBF.
José M. C. Quintas
Harbour 3.2, mingw, gtwvg mt, fivewin 25.04, multithread, dbfcdx, MySQL, ADOClass, PDFClass, SefazClass, (hwgui mt), (hmg3), (hmg extended), (oohg), PNotepad, ASP, stored procedure, stored function, Linux (Flagship/harbour 3.2)
"The world is full of kings and queens, who blind our eyes and steal our dreams Its Heaven and Hell"

https://github.com/JoseQuintas/
Avatar do usuário
JoséQuintas
Administrador
Administrador
Mensagens: 20267
Registrado em: 26 Fev 2007 11:59
Localização: São Paulo-SP

Browse com ADO

Mensagem por JoséQuintas »

Pra que serve esse browse:

pode ser planilha Excel, Access, MySQL, SQL Server, Firebird, Oracle, e qualquer coisa que possua ODBC disponível.
José M. C. Quintas
Harbour 3.2, mingw, gtwvg mt, fivewin 25.04, multithread, dbfcdx, MySQL, ADOClass, PDFClass, SefazClass, (hwgui mt), (hmg3), (hmg extended), (oohg), PNotepad, ASP, stored procedure, stored function, Linux (Flagship/harbour 3.2)
"The world is full of kings and queens, who blind our eyes and steal our dreams Its Heaven and Hell"

https://github.com/JoseQuintas/
Avatar do usuário
JoséQuintas
Administrador
Administrador
Mensagens: 20267
Registrado em: 26 Fev 2007 11:59
Localização: São Paulo-SP

Browse com ADO

Mensagem por JoséQuintas »

Tem uma coisa interessante nesse browse:

Código: Selecionar todos

CASE oBrowse:ApplyKey( nKey ) == TBR_EXIT
Substitui tudo isto, ou pelo menos a parte padrão.

Código: Selecionar todos

      CASE nkey == K_CTRL_PGDN ;  oBrowse:GoBottom() ; LOOP
      CASE nkey == K_CTRL_PGUP ;  oBrowse:GoTop() ;    LOOP
      CASE nkey == K_DOWN ;       oBrowse:Down()    ;  LOOP
      CASE nkey == K_HOME ;       oBrowse:GoTop() ;    LOOP
      CASE nkey == K_END ;        oBrowse:GoBottom() ; LOOP
      CASE nkey == K_LEFT ;       oBrowse:Left() ;     LOOP
      CASE nkey == K_RIGHT ;      oBrowse:Right() ;    LOOP
      CASE nkey == K_PGDN ;       oBrowse:PageDown() ; LOOP
      CASE nkey == K_PGUP ;       oBrowse:PageUp() ;   LOOP
      CASE nkey == K_UP ;         oBrowse:Up() ;       LOOP
      CASE nKey == K_ESC;   EXIT
Acaba deixando a rotina de browse mais enxuta.
Não sei se alguém reparou nisso.
É o que digo sempre: todo fonte pode ter dicas interessantes, é sempre bom olhar com atenção.
José M. C. Quintas
Harbour 3.2, mingw, gtwvg mt, fivewin 25.04, multithread, dbfcdx, MySQL, ADOClass, PDFClass, SefazClass, (hwgui mt), (hmg3), (hmg extended), (oohg), PNotepad, ASP, stored procedure, stored function, Linux (Flagship/harbour 3.2)
"The world is full of kings and queens, who blind our eyes and steal our dreams Its Heaven and Hell"

https://github.com/JoseQuintas/
Avatar do usuário
JoséQuintas
Administrador
Administrador
Mensagens: 20267
Registrado em: 26 Fev 2007 11:59
Localização: São Paulo-SP

Browse com ADO

Mensagem por JoséQuintas »

Nota: editei o fonte anterior, estava com um erro no BrowseADO(), pra não gerar problemas depois.

Aqui um exemplo completo, que basta compilar.

Código: Selecionar todos

#include "tbrowse.ch"
#include "directry.ch"
#define AD_BIGINT   20
#define AD_DATE     7
#define AD_VARCHAR  200

PROCEDURE Main

   LOCAL oTemporario, oTBrowse, oFile, aList

   SetMode( 40, 100 )
   SetCOlor( "W/B","N/w",,,"W/B" )
   CLS
   // cria estrutura
   oTemporario := win_OleCreateObject( "ADODB.Recordset" )
   WITH OBJECT oTemporario:Fields
      :Append( "NOME", AD_VARCHAR, 100 )
      :Append( "TAMANHO", AD_BIGINT, 11 )
      :Append( "DATA", AD_DATE )
      :Append( "HORA", AD_VARCHAR, 8 )
   ENDWITH
   // grava informação
   WITH OBJECT oTemporario
      :Open()
      aList := Directory( "*.*" )
      FOR EACH oFile IN aList
         :AddNew()
         :Fields( "NOME" ):Value := oFile[ F_NAME ]
         :Fields( "TAMANHO" ):Value := oFile[ F_SIZE ]
         :Fields( "DATA" ):Value := oFile[ F_DATE ]
         :Fields( "HORA" ):Value := oFile[ F_TIME ]
         :Update()
      NEXT
   ENDWITH
   oTemporario:MoveFirst()

   oTBrowse := { ;
      { "NOME",     { || Pad( oTemporario:Fields( "NOME" ):Value, 20 ) } }, ;
      { "TAMANHO",  { || Str( oTemporario:Fields( "TAMANHO" ):Value, 20 ) } }, ;
      { "DATA",     { || oTemporario:Fields( "DATA" ):Value } }, ;
      { "HORA",     { || oTemporario:Fields( "HORA" ):Value } } }
   BrowseADO( oTemporario, oTBrowse )

   oTemporario:Close()

   RETURN

FUNCTION BrowseADO( oTemporario, oTBrowse )

   LOCAL oBrowse, nKey, oElement

   oBrowse := TBrowseDB():new( 04, 3, MaxRow() - 7, MaxCol() - 3 )

   oBrowse:goTopBlock  := { || oTemporario:moveFirst() }
   oBrowse:goBottomBlock := { || oTemporario:moveLast() }
   oBrowse:skipBlock  := { | n | ADOSkipper( oTemporario, n ) }

   FOR EACH oElement IN oTBrowse
      oBrowse:AddColumn( TBColumnNew( oElement[ 1 ], oElement[ 2 ] ) )
   NEXT

   DO WHILE .T.
      oBrowse:forceStable()
//      oBrowse:ColorRect( { oBrowse:RowPos, oBrowse:LeftVisible, oBrowse:RowPos, oBrowse:RightVisible }, { 2, 1 } )
//      oBrowse:ColorRect( { oBrowse:RowPos, oBrowse:ColPos, oBrowse:RowPos, oBrowse:ColPos }, { 3, 2 } )
//      oBrowse:refreshCurrent()
      nKey := Inkey(0)
      DO CASE
      CASE oBrowse:ApplyKey( nKey ) == TBR_EXIT
         EXIT
      ENDCASE
   ENDDO

   RETURN NIL

STATIC FUNCTION ADOSkipper( oTemporario, nSkip )

   LOCAL nRec := oTemporario:AbsolutePosition

   IF ! ( oTemporario:Eof )
      oTemporario:Move( nSkip )
      IF oTemporario:Eof
         oTemporario:moveLast()
      ENDIF
      IF oTemporario:Bof
         oTemporario:moveFirst()
      ENDIF
   ENDIF

   RETURN oTemporario:AbsolutePosition - nRec
test1.png
test2.png
José M. C. Quintas
Harbour 3.2, mingw, gtwvg mt, fivewin 25.04, multithread, dbfcdx, MySQL, ADOClass, PDFClass, SefazClass, (hwgui mt), (hmg3), (hmg extended), (oohg), PNotepad, ASP, stored procedure, stored function, Linux (Flagship/harbour 3.2)
"The world is full of kings and queens, who blind our eyes and steal our dreams Its Heaven and Hell"

https://github.com/JoseQuintas/
Avatar do usuário
JoséQuintas
Administrador
Administrador
Mensagens: 20267
Registrado em: 26 Fev 2007 11:59
Localização: São Paulo-SP

Browse com ADO

Mensagem por JoséQuintas »

Faltou acrescentar:

Como dá pra perceber, dá pra usar ADO pra temporários também.
Gostei tanto do browse com ADO, que comecei a usar em outras situações.
Não precisa arquivo em disco, e o Windows se vira com isso.

Quando virar programa gráfico... só usar algum grid/browse equivalente pra ADO...

Pra usar MySQL ou SQL Server ou outro.... não precisa criar nem gravar no temporário, vém pronto do MySQL ou outro.

Algo mais legal ainda:
NÃO vou usar, mas..... no VB6 tem o Crystal Reports e o outro da Microsoft, pra gerar relatórios a partir do recordset ADO.
Poderia ter relatórios automáticos a partir desses recordsets !!!
Ou talvez NET mesmo, já que é grátis... quem sabe....
José M. C. Quintas
Harbour 3.2, mingw, gtwvg mt, fivewin 25.04, multithread, dbfcdx, MySQL, ADOClass, PDFClass, SefazClass, (hwgui mt), (hmg3), (hmg extended), (oohg), PNotepad, ASP, stored procedure, stored function, Linux (Flagship/harbour 3.2)
"The world is full of kings and queens, who blind our eyes and steal our dreams Its Heaven and Hell"

https://github.com/JoseQuintas/
Avatar do usuário
JoséQuintas
Administrador
Administrador
Mensagens: 20267
Registrado em: 26 Fev 2007 11:59
Localização: São Paulo-SP

Browse com ADO

Mensagem por JoséQuintas »

Esse negócio do browse ADO tá muito legal.

Imaginem substituir tudo que é Achoice()* por esse browse.....

Se pesquisar pela inicial já era interessante.... filtrar por qualquer texto é muito melhor...

E fica tudo padronizado, pro usuário ficar craque nisso.... ou sentir falta do recurso, se trocar de aplicativo... rs
José M. C. Quintas
Harbour 3.2, mingw, gtwvg mt, fivewin 25.04, multithread, dbfcdx, MySQL, ADOClass, PDFClass, SefazClass, (hwgui mt), (hmg3), (hmg extended), (oohg), PNotepad, ASP, stored procedure, stored function, Linux (Flagship/harbour 3.2)
"The world is full of kings and queens, who blind our eyes and steal our dreams Its Heaven and Hell"

https://github.com/JoseQuintas/
cjp
Usuário Nível 6
Usuário Nível 6
Mensagens: 1563
Registrado em: 19 Nov 2010 22:29
Localização: paraná
Contato:

Browse com ADO

Mensagem por cjp »

Por favor, preciso de ajuda neste Browse com ADO, com um pequeno detalhe:

Meu código:

Código: Selecionar todos

      oTBrowse := TBrowseDB():new( 05, 3, MaxRow() - 7, MaxCol() - 2 )

      oTBrowse:goTopBlock    := { || oRs:moveFirst() }
      oTBrowse:goBottomBlock := { || oRs:moveLast() }
      oTBrowse:skipBlock     := { | n | ADORecordSetSkipper( oRs, n ) }

      nLen := oRs:fields():count() - 1
      FOR i := 0 TO nLen
         oColumn       := TBColumnNew( oRs:fields(i):name(), ADORecordSetFieldBlock( oRs, i ) )
         oColumn:width := Max( Min( oRs:Fields(i):definedSize,50), Len( oRs:fields(i):name ) )
         oTBrowse:addColumn( oColumn )
      NEXT
Só preciso alterar uma pequena coisa: alterar o campo data (primeiro campo), que não está aparecendo completo. Imagino que o problema seja nesta linha:

Código: Selecionar todos

         oColumn:width := Max( Min( oRs:Fields(i):definedSize,50), Len( oRs:fields(i):name ) )
Mas não sei como alterá-la para corrigir este problema.

Podem me ajudar?
Anexos
tbrowse.png
Inacio de Carvalho Neto
Avatar do usuário
JoséQuintas
Administrador
Administrador
Mensagens: 20267
Registrado em: 26 Fev 2007 11:59
Localização: São Paulo-SP

Browse com ADO

Mensagem por JoséQuintas »

O Browse deste post não tem esse problema.

A saída pra esse outro é ir ajustando conforme a necessidade.
Exemplo:

Código: Selecionar todos

IF ValType( oRs:Fields(i):Value ) != "D"
   nFieldLen := Min( oRs:Fields(I):DefinedSize, 50 )
   oColumn:Width := Max( nFieldLen, Len( oRs:fields(i):name ) )
ENDIF
ou

Código: Selecionar todos

IF ValType( oRs:Fields(i):Value ) == "D"
   nFieldLen := Len( Dtoc( Date() ) )
ELSE
   nFieldLen := Min( oRs:Fields(I):DefinedSize, 50 )
ENDIF
oColumn:Width := Max( nFieldLen, Len( oRs:fields(i):name ) )
José M. C. Quintas
Harbour 3.2, mingw, gtwvg mt, fivewin 25.04, multithread, dbfcdx, MySQL, ADOClass, PDFClass, SefazClass, (hwgui mt), (hmg3), (hmg extended), (oohg), PNotepad, ASP, stored procedure, stored function, Linux (Flagship/harbour 3.2)
"The world is full of kings and queens, who blind our eyes and steal our dreams Its Heaven and Hell"

https://github.com/JoseQuintas/
cjp
Usuário Nível 6
Usuário Nível 6
Mensagens: 1563
Registrado em: 19 Nov 2010 22:29
Localização: paraná
Contato:

Browse com ADO

Mensagem por cjp »

Resolveu, muito obrigado.
Inacio de Carvalho Neto
cjp
Usuário Nível 6
Usuário Nível 6
Mensagens: 1563
Registrado em: 19 Nov 2010 22:29
Localização: paraná
Contato:

Browse com ADO

Mensagem por cjp »

Teria como colocar divisores entre as colunas, como no velho browse()?
Inacio de Carvalho Neto
Avatar do usuário
JoséQuintas
Administrador
Administrador
Mensagens: 20267
Registrado em: 26 Fev 2007 11:59
Localização: São Paulo-SP

Browse com ADO

Mensagem por JoséQuintas »

Sim, é só usar as variáveis que existem no tbrowse pra isso.

Código: Selecionar todos

   oBrowse:HeadSep       := Chr(196)
   oBrowse:ColSep        := Chr(179)
   oBrowse:FootSep       := ""
José M. C. Quintas
Harbour 3.2, mingw, gtwvg mt, fivewin 25.04, multithread, dbfcdx, MySQL, ADOClass, PDFClass, SefazClass, (hwgui mt), (hmg3), (hmg extended), (oohg), PNotepad, ASP, stored procedure, stored function, Linux (Flagship/harbour 3.2)
"The world is full of kings and queens, who blind our eyes and steal our dreams Its Heaven and Hell"

https://github.com/JoseQuintas/
cjp
Usuário Nível 6
Usuário Nível 6
Mensagens: 1563
Registrado em: 19 Nov 2010 22:29
Localização: paraná
Contato:

Browse com ADO

Mensagem por cjp »

Deu certo, muito obrigado.
Inacio de Carvalho Neto
cjp
Usuário Nível 6
Usuário Nível 6
Mensagens: 1563
Registrado em: 19 Nov 2010 22:29
Localização: paraná
Contato:

Browse com ADO

Mensagem por cjp »

Estou tentando expandir meu uso desse browse, e surgiram duas necessidades:

1) como faço para mostrar no browse apenas alguns campos, não todos?

2) como faço para editar um registro? Na verdade só preciso ler o registro inteiro, não quero alterá-lo.
Inacio de Carvalho Neto
Avatar do usuário
JoséQuintas
Administrador
Administrador
Mensagens: 20267
Registrado em: 26 Fev 2007 11:59
Localização: São Paulo-SP

Browse com ADO

Mensagem por JoséQuintas »

cjp escreveu:1) como faço para mostrar no browse apenas alguns campos, não todos?
Caso não tenha percebido, o browse deste post é pra isso.
cjp escreveu:2) como faço para editar um registro? Na verdade só preciso ler o registro inteiro, não quero alterá-lo.
Acho que quer ter acesso ao registro atual.
Como o recordset fica na variável, é só usar a variável.
José M. C. Quintas
Harbour 3.2, mingw, gtwvg mt, fivewin 25.04, multithread, dbfcdx, MySQL, ADOClass, PDFClass, SefazClass, (hwgui mt), (hmg3), (hmg extended), (oohg), PNotepad, ASP, stored procedure, stored function, Linux (Flagship/harbour 3.2)
"The world is full of kings and queens, who blind our eyes and steal our dreams Its Heaven and Hell"

https://github.com/JoseQuintas/
cjp
Usuário Nível 6
Usuário Nível 6
Mensagens: 1563
Registrado em: 19 Nov 2010 22:29
Localização: paraná
Contato:

Browse com ADO

Mensagem por cjp »

Desculpe, eu não fui claro antes.

Eu preciso editar um campo, mas o problema é saber qual é o campo escolhido pelo usuário para isso.

No velho dbedit(), usava modo e coluna para isso. No tbrowse tem algo semelhante?
Inacio de Carvalho Neto
Responder