Pular para o conteúdo principal

Postagem em destaque

BlackTDN :: LeetCode :: Comparando Implementações Harbour e TLPP para o Desafio Longest Palindromic Substring

_Créditos das imagens: ChatGPT_ ### LeetCode :: Comparando Implementações Harbour e TLPP para o Desafio Longest Palindromic Substring Resolver o problema do [Longest Palindromic Substring](https://leetcode.com/problems/longest-palindromic-substring/description/) é um exercício clássico de programação, que desafia desenvolvedores a encontrar a maior substring palindrômica dentro de uma string. Recentemente, exploramos soluções tanto em Harbour quanto em TLPP (Total Language Protheus Programming). Neste artigo, comparamos as implementações nessas duas linguagens, destacando suas semelhanças, diferenças e funcionalidades específicas. #### Implementações em Harbour ##### Versão 5.1 Essa solução utiliza a técnica de expansão a partir do centro do palíndromo. Cada caractere ou par de caracteres consecutivos é considerado um possível "centro". O algoritmo expande em ambas as direções enquanto os caracteres forem iguais, retornando o maior palíndromo encontrado. ##### Versão 5....

Protheus :: Filtrando a mBrowse de acordo com a Legenda de Cores

O Filtro da mBrowse, baseado na Legenda de Cores, é algo que já deveria existir no sistema padrão. Ele facilitaria muito a vida do usuário mas, infelizmente, isso não é uma verdade. Quem sabe, após este "post", a totvs/microsiga não decida implementa-lo em versões futuras do protheus/by you.

Enquanto isso não se torna realidade, vou postar aqui uma dica e disponibilizar um exemplo de código fonte de: "Como Implementar o Filtro da mBrowse baseado na Legenda de Cores".

Dada a característica da implementação atual das cores e legenda na mBrowse, esse, acredito eu, seja o maior "POG" que já implementei usando Advpl. Ele é funcional, é elegante, mas não deixa de ser um "POG".

Ele passa a ser um "POG" à partir do momento que tenho que "roubar" (parafraseando Wilson de Godoy) a Legenda de cores bem como a regra de sua implementação usando "tratamento de erro" para criar uma função de propósito geral (pois servirá para toda e qualquer mBrowse que possua legenda e cujo programa nos permita "roubar" essas características), e específico, pois será utilizado para o fim a que se propõe.

A função terá duas características principais:

A primeira será retornar a Descrição da Legenda de acordo com a sua condição: útil para a impressão de relatórios;

A segunda, retornara a expressão advpl que será utilizada para a implementação do Filtro.

Bem. Vamos ao código.

Utilizarei, nesse exemplo, os programas MATA110 (Solicitação de Compras) e MATA120 (Pedido de Compras) através dos seguintes "Pontos de Entrada":

Para o MATA110:

MTA110MNU - Ponto de Entrada MTA110MNU, executado na MATA110, na MenuDef, sera utilizado alterar as Opcoes do aRotina;

MT110LEG - Implementacao do Ponto de Entrada MT110LEG executado na funcao A110Legenda do programa MATA110 para adicionar novos elementos na Legenda;

MT110COR - Implementacao do Ponto de Entrada MT110COR executado na funcao MATA110 do programa MATA110 Tratamento de cores na mBrowse; e

Para o MATA120:

MT120BRW - Implementacao do Ponto de Entrada MT120BRW para a Inclusao de Novas Opcoes no Menu do aRotina do programa MATA120;

MT120LEG - Implementacao do Ponto de Entrada MT120LEG executado na funcao A120Legenda do programa MATA120 para adicionar novos elementos na Legenda;

MT120COR - Implementacao do Ponto de Entrada MT120COR executado na funcao MATA120 do programa MATA120 Tratamento de cores na mBrowse.


O Programa u_mBrowseLFilter.PRG contém todas as funções basicas para o tratameto de filtro na mBrowse
#INCLUDE "PROTHEUS.CH"
#INCLUDE "TRYEXCEPTION.CH"

Static __cMbrRstFilter

/*/
 Funcao:  BrwLegenda
 Autor:  Marinaldo de Jesus
 Data:  22/04/2011
 Descricao: Legenda de Cores
 Sintaxe: StaticCall( u_mBrowseLFilter , BrwLegenda , cTitulo , cMensagem , aLegend , bAction , cMsgAction )
/*/
Static Function BrwLegenda( cTitulo , cMensagem , aLegend , bAction , cMsgAction )

 Local aListBox

 Local nItem
 Local nItens

 Local oDlg
 Local oFont
 Local oListBox

 BEGIN SEQUENCE

  DEFAULT aLegend  := {}
  nItens     := Len( aLegend )
  
  IF ( nItens == 0 )
   BREAK
  EndIF

  DEFAULT cTitulo  := "BrwLegenda"
  DEFAULT cMensagem := ""
  DEFAULT bAction  := { |cResName| !Empty( cResName ) }
  DEFAULT cMsgAction := ""

  aListBox := Array( nItens , 3 )
  For nItem := 1 To nItens
   aListBox[ nItem ][ 1 ] := LoadBitmap( GetResources() , aLegend[ nItem ][ 1 ] )
   aListBox[ nItem ][ 2 ] := aLegend[ nItem ][ 2 ]
  Next nItem 

  DEFINE MSDIALOG oDlg FROM 0,0 TO 345,410 TITLE OemToAnsi( cTitulo ) OF GetWndDefault() PIXEL

   DEFINE FONT oFont NAME "Arial" SIZE 0, -13 BOLD

   @ 03 , 05 SAY OemToAnsi( cMensagem ) OF oDlg PIXEL SIZE 200 , 010 FONT oFont
   @ 11 , 05 TO 012 , 200 LABEL "" OF oDlg PIXEL

   @ 15 , 05 LISTBOX oListBox FIELDS HEADER " ", "Status" SIZE 200 , 150 OF oDlg PIXEL

   oListBox:SetArray( aListBox )
   oListBox:bLDblClick   := { || Eval( bAction , aLegend[ oListBox:nAt][ 1 ] ) , oDlg:End() }
   oListBox:bLine    := { || { aListBox[ oListBox:nAt ][ 01 ] , aListBox[ oListBox:nAt ][ 02 ] }  }
   oListBox:cToolTip   := OemToAnsi( cMsgAction )
   oListBox:Refresh()

  ACTIVATE MSDIALOG oDlg CENTERED

 END SEQUENCE  

Return( NIL )

/*/
 Funcao:  BrwGetSLeg
 Autor:  Marinaldo de Jesus
 Data:  22/04/2011
 Descricao: Retornar o Status  conforme Array de Cores da mBrowse
 Sintaxe: StaticCall( u_mBrowseLFilter , BrwGetSLeg , cAlias , bGetColors , bGetLegend , cResName , lArrColors )
/*/
Static Function BrwGetSLeg( cAlias , bGetColors , bGetLegend , cResName , lArrColors )

 Local cBmpColor  := ""

 Local lFilter  := ( ValType( cResName ) == "C" )

 Local nLoop
 Local nLoops

 Local uC1Ret

 Private __aColors_ := {}
 Private __aLegend_ := {}

 TRYEXCEPTION
  Eval( bGetColors )  //Obtem __aColors_
 ENDEXCEPTION

 TRYEXCEPTION
  Eval( bGetLegend )  //Obtem __aLegend_
 ENDEXCEPTION

 BEGIN SEQUENCE

  DEFAULT lArrColors := .F.
  IF ( lArrColors )
   uC1Ret := { __aColors_ , __aLegend_ }
   BREAK
  EndIF

  TRYEXCEPTION
   IF ( lFilter )
    cResName := Upper( AllTrim( cResName ) )
   EndIF
   DEFAULT cAlias := Alias()
   nLoops := Len( __aColors_ )
   For nLoop := 1 To nLoops
    IF ( lFilter )
     cBmpColor  := Upper( AllTrim( __aColors_[ nLoop ][ 2 ] ) )
     nPosBmp   := aScan( __aLegend_ , { |aBmpLeg| Upper( AllTrim( aBmpLeg[ 1 ] ) ) == cBmpColor } )
     IF !( nPosBmp == 0 )
      uC1Ret := __aColors_[ nLoop ][ 1 ]       //Obtem a Condicao de Filtro
     EndIF 
    Else
     IF ( cAlias )->( &( __aColors_[ nLoop ][ 1 ] ) )    //Analisa a Condicao
      cBmpColor  := Upper( AllTrim( __aColors_[ nLoop ][ 2 ] ) )
      nPosBmp   := aScan( __aLegend_ , { |aBmpLeg| Upper( AllTrim( aBmpLeg[ 1 ] ) ) == cBmpColor } )
      IF !( nPosBmp == 0 )
       uC1Ret := OemToAnsi( __aLegend_[ nPosBmp ][ 2 ] )  //Obtem a Descricao
      EndIF 
      Exit
     EndIF
    EndIF
   Next nLoop
   DEFAULT uC1Ret := ""
  CATCHEXCEPTION
   uC1Ret := ""
  ENDEXCEPTION    

 END SEQUENCE

Return( uC1Ret )

/*/
 Funcao:  BrwFiltLeg
 Autor:  Marinaldo de Jesus
 Data:  22/04/2011
 Descricao: Filtra o Browse de acordo com a Opcao da Legenda da mBrowse
 Sintaxe: StaticCall( u_mBrowseLFilter , BrwFiltLeg , cAlias , aColors , aLegend , cTitle , cMsg , cMsgAction , cVarName )
/*/
Static Function BrwFiltLeg( cAlias , aColors , aLegend , cTitle , cMsg , cMsgAction , cVarName )

 Local aIndex

 Local bAction := { |cResName| cBmpName := cResName }
 
 Local cBmpName
 Local cExpFilter
 Local cSvExprFilTop
 
 Local nBmpPos

 BrwLegenda( OemToAnsi( cTitle ) , OemToAnsi( cMsg ) , @aLegend , bAction , OemToAnsi( cMsgAction ) )

 nBmpPos   := aScan( aColors , { |aBmp| Upper( AllTrim( aBmp[2] ) ) == cBmpName } )
 IF ( nBmpPos > 0 )
  cExpFilter := aColors[ nBmpPos ][ 1 ]
 Else
  cExpFilter := ""
 EndIF

 cSvExprFilTop := ( cAlias )->( dbFilter() )
 __cMbrRstFilter := cSvExprFilTop
 IF ( Type( cVarName ) == "C" )
  &( cVarName ) := cSvExprFilTop
 EndIF

 aIndex   := {}
 EndFilBrw( cAlias , @aIndex )
 ( cAlias )->( dbClearFilter() )
 bFiltraBrw   := { || FilBrowse( cAlias , @aIndex , @cExpFilter ) }
 Eval( bFiltraBrw )

 oObjBrow := GetObjBrow()
 oObjBrow:ResetLen()
 oObjBrow:GoTop()
 oObjBrow:Refresh()

Return( cSvExprFilTop )

/*/
 Funcao:  MbrRstFilter
 Autor:  Marinaldo de Jesus
 Data:  22/04/2011
 Descricao: Restaura o Filtro de Browse
 Sintaxe: StaticCall( u_mBrowseLFilter , MbrRstFilter, cAlias , cVarName )
/*/
Static Function MbrRstFilter( cAlias , cVarName )
 
 Local aIndex
 Local oObjBrow
 Local cMbrRstFilter
 
 IF ( ( ValType( cVarName )== "C" ) )
  cMbrRstFilter := &( cVarName )
 Else
  cMbrRstFilter := &( __cMbrRstFilter )
 EndIF

 aIndex   := {}
 EndFilBrw( cAlias , @aIndex )
 ( cAlias )->( dbClearFilter() )
 bFiltraBrw   := { || FilBrowse( cAlias , @aIndex , @cMbrRstFilter ) }
 Eval( bFiltraBrw )

 oObjBrow := GetObjBrow()
 oObjBrow:ResetLen()
 oObjBrow:GoTop()
 oObjBrow:Refresh()

Return( NIL )

/*/
 Funcao:  __Dummy
 Autor:  Marinaldo de Jesus
 Data:  22/04/2011
 Descricao: __Dummy (nao faz nada, apenas previne warning de compilacao)
 Sintaxe: 
/*/
Static Function __Dummy( lRecursa )
 Local oException
 TRYEXCEPTION
  DEFAULT lRecursa := .F.
  IF !( lRecursa )
   BREAK
  EndIF
  BrwLegenda()
  BrwGetSLeg()
  BrwFiltLeg()
  MbrRstFilter()
  lRecursa := __Dummy( .F. )
 CATCHEXCEPTION USING oException
 ENDEXCEPTION
Return( lRecursa )


Para implementar o filtro na mBrowse do Programa MATA110 (Solicitação de Compras) Fariamos:

Ponto de Entrada MT110LEG : Implementar Legendas Especificas e/ou Retorna-las para o Filtro da mBrowse
#INCLUDE "PROTHEUS.CH"
/*/
 Funcao:  MT110LEG
 Autor:  Marinaldo de Jesus
 Descricao: Implementacao do Ponto de Entrada MT110LEG executado na funcao A110Legenda
    do programa MATA110 para adicionar novos elementos na Legenda
/*/
User Function MT110LEG()
 
 Local aLegend := ParamIxb[1] //Obtenho a Legenda padrao

 //Testo o Tipo
 IF !( ValType( aLegend ) == "A" )
  aLegend := {}
 EndIF
 
 /*/
  Se necessario, adiciono novos elementos aa Legenda Padrao
    
  aAdd( aLegend , { "CRDIMG16"  , OemToAnsi( "Em Pré-Analise" ) } )
  aAdd( aLegend , { "CFGIMG16"  , OemToAnsi( "Suspensa ou Aguardando Alterações" ) } )
 /*/

 //Verifico se estou querendo, apenas, as informacoes da Legenda
 IF IsInCallStack( "GetC1Status" )
  //"Roubo"/Recupero as Informacoes da Legenda de Cores
  __aLegend_ := aLegend
  //Forco o Erro
  UserException( "IGetC1Status" )
 EndIF

Return( aLegend )


Ponto de Entrada MT110COR : Implementar Regra para cores e/ou Retorna-las para o Filtro da mBrowse
#INCLUDE "PROTHEUS.CH"
#INCLUDE "TRYEXCEPTION.CH"
/*/
 Funcao:  MT110COR
 Autor:  Marinaldo de Jesus
 Descricao: Implementacao do Ponto de Entrada MT110COR executado na funcao MATA110
    do programa MATA110 Tratamento de cores na mBrowse
/*/
User Function MT110COR()

 Local aCores := ParamIxb[1] //Obtenho a Legenda padrao
 
 Local nBmpPos

 //Testo o Tipo
 IF !( ValType( aCores ) == "A" )
  aCores := {}
 EndIF
    
 /*/
  Se necessario, adiciono novos elementos aa Legenda Padrao

  IF nToL(SC1->( FieldPos( "C1_APROV" ) ) )
 
   aAdd( aCores , { "C1_APROV=='1'" , "CRDIMG16" } )  //"Em Pré-Analise"
   aAdd( aCores , { "C1_APROV=='2'" , "CFGIMG16" } )  //"Suspensa ou Aguardando Alterações"
 
  EndIF
 /*/
  
 nBmpPos := aScan( aCores , { |aBmp| Upper( AllTrim( aBmp[2] ) ) == "BR_AMARELO" } )
 IF ( nBmpPos > 0 )
  IF !( "C1_QUANT" $ aCores[ nBmpPos ][1] )
   aCores[ nBmpPos ][1] += " .AND. C1_QUJE<>C1_QUANT" //Redefino SC Parcialmente Atendida (Tem um BUG na Logica padrao)
  EndIF 
 EndIF

 //Verifico se estou querendo, apenas, as informacoes da Legenda
 IF IsInCallStack( "GetC1Status" )
  //"Roubo"/Recupero as Informacoes da Legenda de Cores
  __aColors_ := aCores
  //Forco o Erro
  UserException( "IGetC1Status" )
 EndIF

Return( aCores )      

/*/
 Funcao:  GetC1Status
 Autor:  Marinaldo de Jesus
 Descricao: Retornar o Status da SC1 conforme Array de Cores da mBrowse
 Sintaxe: StaticCall( U_MT110COR , GetC1Status , cAlias , cResName , lArrColors )
/*/
Static Function GetC1Status( cAlias , cResName , lArrColors )

 Local bGetColors := { || Mata110() }   
 Local bGetLegend := { || A110Legenda() }

 DEFAULT cAlias   := "SC1"

Return( StaticCall( u_mBrowseLFilter , BrwGetSLeg , @cAlias , @bGetColors , @bGetLegend , @cResName , @lArrColors ) )

/*/
 Funcao:  __Dummy
 Autor:  Marinaldo de Jesus
 Data:  22/04/2011
 Descricao: __Dummy (nao faz nada, apenas previne warning de compilacao)
 Sintaxe: 
/*/
Static Function __Dummy( lRecursa )
 Local oException
 TRYEXCEPTION
  DEFAULT lRecursa := .F.
  IF !( lRecursa )
   BREAK
  EndIF
  GetC1Status()
  lRecursa := __Dummy( .F. )
 CATCHEXCEPTION USING oException
 ENDEXCEPTION
Return( lRecursa )


Ponto de Entrada MTA110MNU: Implementar a Chamada as Funcoes no Menu aRotina da mBrowse
#INCLUDE "PROTHEUS.CH"
#INCLUDE "TRYEXCEPTION.CH"
/*/
 Funcao:  MTA110MNU
 Autor:  Marinaldo de Jesus
 Data:  07/01/2011
 Descricao: Ponto de Entrada MTA110MNU, executado na MATA110, na MenuDef, sera utilizado alterar as Opcoes do aRotina
/*/
User Function MTA110MNU()

 Local aMenuPopUp

 Local nIndex

 TRYEXCEPTION
 
  //Testo o Tipo
  IF !( Type( "aRotina" ) == "A" )
   BREAK
  EndIF

  PUBLIC __cSC1FMbr //Ira armazenar o Filtro Atual

  //Adiciono Novo Sub-Menu ao Menu aRotina
  aMenuPopUp := {}

  aAdd( aMenuPopUp , Array( 4 ) )
  nIndex   := Len( aMenuPopUp )

  aMenuPopUp[nIndex][1] := OemToAnsi( "Filtrar Legenda" )
  aMenuPopUp[nIndex][2] := "StaticCall( U_MTA110MNU , SC1FiltLeg )"
  aMenuPopUp[nIndex][3] := 0
  aMenuPopUp[nIndex][4] := 3

  aAdd( aMenuPopUp , Array( 4 ) )
  nIndex   := Len( aMenuPopUp )

  aMenuPopUp[nIndex][1] := OemToAnsi( "Limpar Filtro" )
  aMenuPopUp[nIndex][2] := "StaticCall( U_MTA110MNU , MbrRstFilter )"
  aMenuPopUp[nIndex][3] := 0
  aMenuPopUp[nIndex][4] := 3

  //Adiciono uma nova Opcao no Menu aRotina
  aAdd( aRotina , Array( 4 ) )
  nIndex  := Len( aRotina )
  aRotina[ nIndex ][1] := "Filtro &Legenda"
  aRotina[ nIndex ][2] := aMenuPopUp
  aRotina[ nIndex ][3] := 0
  aRotina[ nIndex ][4] := 1

 CATCHEXCEPTION USING oException

  IF ( ValType( oException ) == "O" )
   Help( "" , 1 , ProcName() , NIL , OemToAnsi( oException:Description ) , 1 , 0 )
   ConOut( CaptureError() )
  EndIF

 ENDEXCEPTION  

Return( NIL )

/*/
 Funcao:  SC1FiltLeg
 Autor:  Marinaldo de Jesus
 Data:  15/03/2011
 Descricao: Filtra o Browse de acordo com a Opcao da Legenda da mBrowse
/*/
Static Function SC1FiltLeg()

 Local aGetSc1
 Local aColors
 Local aLegend

 Local cSvExprFilTop

 aGetSc1   := StaticCall( U_MT110COR , GetC1Status , "SC1" , NIL , .T. )
 aColors   := aGetSc1[1]
 aLegend   := aGetSc1[2]

 cSvExprFilTop := StaticCall( u_mBrowseLFilter , BrwFiltLeg , "SC1" , @aColors , @aLegend , "Solicitação de Compras" , "Legenda" , "Duplo Clique para ativar o Filtro" , "__cSC1FMbr" )

Return( cSvExprFilTop )

/*/
 Funcao:  MbrRstFilter
 Autor:  Marinaldo de Jesus
 Data:  15/03/2011
 Descricao: Restaura o Filtro de Browse
/*/
Static Function MbrRstFilter()
Return( StaticCall( u_mBrowseLFilter , MbrRstFilter , "SC1" , "__cSC1FMbr" ) )

/*/
 Funcao:  __Dummy
 Autor:  Marinaldo de Jesus
 Data:  22/04/2011
 Descricao: __Dummy (nao faz nada, apenas previne warning de compilacao)
 Sintaxe: 
/*/
Static Function __Dummy( lRecursa )
 Local oException
 TRYEXCEPTION
  DEFAULT lRecursa := .F.
  IF !( lRecursa )
   BREAK
  EndIF
     SC1FromAC9()
     SC1FiltLeg()
     MbrRstFilter()
  lRecursa := __Dummy( .F. )
 CATCHEXCEPTION USING oException
 ENDEXCEPTION
Return( lRecursa )


Para implementar o filtro na mBrowse do Programa MATA120 (Pedidos de Compras) Fariamos:

Ponto de Entrada MT120LEG : Implementar Legendas Especificas e/ou Retorna-las para o Filtro da mBrowse

#INCLUDE "PROTHEUS.CH"
/*/
 Funcao:  MT120LEG
 Autor:  Marinaldo de Jesus
 Descricao: Implementacao do Ponto de Entrada MT120LEG executado na funcao A120Legenda
    do programa MATA120 para adicionar novos elementos na Legenda
/*/
User Function MT120LEG()
 
 Local aLegend := ParamIxb[1] ////Obtenho a Legenda padrao

 //Testo o Tipo
 IF !( ValType( aLegend ) == "A" )
  aLegend := {}
 EndIF

 /*/
  Se necessario, adiciono novos elementos aa Legenda Padrao
  
  aAdd( aLegend , { "RNPSOLICITACNT_16" , OemToAnsi( "Solicitação de Contrato" ) } )
  aAdd( aLegend , { "RNPADITIVOCNT_16" , OemToAnsi( "Solicitação de Aditivo"  ) } )
  aAdd( aLegend , { "BPMSDOCA_16"   , OemToAnsi( "Bloqueado por Contrato"  ) } )
  aAdd( aLegend , { "CADEADO_16"   , OemToAnsi( "Bloqueado por Orçamento" ) } )
 
 /*/ 

 //Verifico se estou querendo, apenas, as informacoes da Legenda
 IF IsInCallStack( "GetC7Status" )
  //"Roubo"/Recupero as Informacoes da Legenda de Cores
  __aLegend_ := aLegend
  //Forco o Erro
  UserException( "IGetC7Status" )
 EndIF

Return( aLegend )


Ponto de Entrada MT120COR : Implementar Regra para cores e/ou Retorna-las para o Filtro da mBrowse

#INCLUDE "PROTHEUS.CH"
#INCLUDE "TRYEXCEPTION.CH"
/*/
 Funcao:  MT120COR
 Autor:  Marinaldo de Jesus
 Descricao: Implementacao do Ponto de Entrada MT120COR executado na funcao MATA120
    do programa MATA120 Tratamento de cores na mBrowse
/*/
User Function MT120COR()

 Local aCores  := ParamIxb[1] //Obtenho a Legenda padrao
 
* Local cC7XCTNCNB := Space( GetSx3Cache( "C7_XCTNCNB" , "X3_TAMANHO" ) ) //Tratamento especifico para novos elementos

 //Testo o Tipo
 IF !( ValType( aCores ) == "A" )
  aCores := {}
 EndIF

 /*/
  
  Se necessario, adiciono novos elementos aa Legenda Padrao
    
  aAdd( aCores , { "C7_XCNTSOL .and. !C7_XCNTADT .and. C7_XCTNCNB == '" +cC7XCTNCNB + "'"    , "RNPSOLICITACNT_16" } )  //"Solicitação de Contrato"
  aAdd( aCores , { "C7_XCNTSOL .and. C7_XCNTADT .and. C7_XCTNCNB == '" +cC7XCTNCNB + "'"    , "RNPADITIVOCNT_16" } )  //"Solicitação de Aditivo"
  aAdd( aCores , { "C7_CONAPRO=='B' .and. C7_XCTNCNB <> '" +cC7XCTNCNB + "' .and. C7_QUJE>=C7_QUANT" , "BPMSDOCA_16"   } )  //"Bloqueado por Contrato"
  aAdd( aCores , { ".F."                     , "CADEADO_16"   } )  //"Bloqueado por Orçamento"
  
 /*/  
 
 //Verifico se estou querendo, apenas, as informacoes da Legenda
 IF IsInCallStack( "GetC7Status" )
  //"Roubo"/Recupero as Informacoes da Legenda de Cores
  __aColors_ := aCores
  //Forco o Erro
  UserException( "IGetC7Status" )
 EndIF

Return( aCores )

/*/
 Funcao:  GetC7Status
 Autor:  Marinaldo de Jesus
 Descricao: Retornar o Status da SC7 conforme Array de Cores da mBrowse
 Sintaxe: StaticCall( U_MT120COR , GetC7Status , cAlias , cResName , lArrColors )
/*/
Static Function GetC7Status( cAlias , cResName , lArrColors )

 Local bGetColors := { || Mata120() }
 Local bGetLegend := { || A120Legenda() }

 DEFAULT cAlias   := "SC7"

Return( StaticCall( u_mBrowseLFilter , BrwGetSLeg , @cAlias , @bGetColors , @bGetLegend , @cResName , @lArrColors ) )

/*/
 Funcao:  __Dummy
 Autor:  Marinaldo de Jesus
 Data:  22/04/2011
 Descricao: __Dummy (nao faz nada, apenas previne warning de compilacao)
 Sintaxe: 
/*/
Static Function __Dummy( lRecursa )
 Local oException
 TRYEXCEPTION
  DEFAULT lRecursa := .F.
  IF !( lRecursa )
   BREAK
  EndIF
  GetC7Status()
  lRecursa := __Dummy( .F. )
 CATCHEXCEPTION USING oException
 ENDEXCEPTION
Return( lRecursa )


Ponto de Entrada MTA110BRW: Implementar a Chamada as Funcoes no Menu aRotina da mBrowse

#INCLUDE "PROTHEUS.CH"
#INCLUDE "TRYEXCEPTION.CH"
/*/
 Funcao:  MT120BRW
 Autor:  Marinaldo de Jesus
 Data:  22/12/2010
 Descricao: Implementacao do Ponto de Entrada MT120BRW para a Inclusao de Novas Opcoes no Menu do aRotina do programa MATA120
/*/
User Function MT120BRW()

 Local aMnuPopUP
 
 Local cMsgHelp

 Local nIndex

 Local oException

 TRYEXCEPTION

  //Testo o Tipo
  IF !( Type( "aRotina" ) == "A" )
   BREAK
  EndIF

  PUBLIC __cSC7FMbr //Ira armazenar o Filtro Atual

  //Adiciono Novo Sub-Menu ao Menu aRotina
  aMenuPopUp := {}

  aAdd( aMenuPopUp , Array( 4 ) )
  nIndex   := Len( aMenuPopUp )

  aMenuPopUp[nIndex][1] := OemToAnsi( "Filtrar Legenda" )
  aMenuPopUp[nIndex][2] := "StaticCall( U_MT120BRW , SC7FiltLeg )"
  aMenuPopUp[nIndex][3] := 0
  aMenuPopUp[nIndex][4] := 3 

  aAdd( aMenuPopUp , Array( 4 ) )
  nIndex   := Len( aMenuPopUp )

  aMenuPopUp[nIndex][1] := OemToAnsi( "Limpar Filtro" )
  aMenuPopUp[nIndex][2] := "StaticCall( U_MT120BRW , MbrRstFilter )"
  aMenuPopUp[nIndex][3] := 0
  aMenuPopUp[nIndex][4] := 3

  //Adiciono uma nova Opcao no Menu aRotina
  aAdd( aRotina , Array( 4 ) )
  nIndex  := Len( aRotina )
  aRotina[ nIndex ][1] := "Filtro &Legenda"
  aRotina[ nIndex ][2] := aMenuPopUp
  aRotina[ nIndex ][3] := 0
  aRotina[ nIndex ][4] := 1

 CATCHEXCEPTION USING oException

  IF ( ValType( oException ) == "O" )
   cMsgHelp := oException:Description
   Help( "" , 1 , ProcName() , NIL , OemToAnsi( cMsgHelp ) , 1 , 0 )
   ConOut( CaptureError() )
  EndIF

 ENDEXCEPTION

Return( NIL )

/*/
 Funcao:  SC7FiltLeg
 Autor:  Marinaldo de Jesus
 Data:  20/03/2011
 Descricao: Filtra o Browse de acordo com a Opcao da Legenda da mBrowse
/*/
Static Function SC7FiltLeg()

 Local aGetSC7
 Local aColors
 Local aLegend

 Local cSvExprFilTop

 aGetSC7   := StaticCall( U_MT120COR , GetC7Status , "SC7" , NIL , .T. )
 aColors   := aGetSC7[1]
 aLegend   := aGetSC7[2]

 cSvExprFilTop := StaticCall( u_mBrowseLFilter , BrwFiltLeg , "SC7" , @aColors , @aLegend , "Solicitação de Compras" , "Legenda" , "Duplo Clique para ativar o Filtro" , "__cSC7FMbr" )

Return( cSvExprFilTop )

/*/
 Funcao:  MbrRstFilter
 Autor:  Marinaldo de Jesus
 Data:  20/03/2011
 Descricao: Restaura o Filtro de Browse
/*/
Static Function MbrRstFilter()
Return( StaticCall( u_mBrowseLFilter , MbrRstFilter , "SC7" , "__cSC7FMbr" ) )

/*/
 Funcao:  __Dummy
 Autor:  Marinaldo de Jesus
 Data:  22/04/2011
 Descricao: __Dummy (nao faz nada, apenas previne warning de compilacao)
 Sintaxe: 
/*/
Static Function __Dummy( lRecursa )
 Local oException
 TRYEXCEPTION
  DEFAULT lRecursa := .F.
  IF !( lRecursa )
   BREAK
  EndIF
  SC7FiltLeg()
  MbrRstFilter()
  lRecursa := __Dummy( .F. )
 CATCHEXCEPTION USING oException
 ENDEXCEPTION
Return( lRecursa )


Para obter a Descrição da Legenda de Solicitação de Compras Fariamos algo como:

#INCLUDE "PROTHEUS.CH"
#INCLUDE "TBICONN.CH"
User Function C1LStatus()

 Local cC1DLStatus

 PREPARE ENVIRONMENT EMPRESA "01" FILIAL "01"

  ChkFile( "SC1" )
  While SC1->( !Eof() )
 
   //Obtenho a Descricao do Status
   cC1DLStatus := StaticCall( U_MT110COR , GetC1Status )
   
   //Direciono a Saida para o Console do Server
   ConOut( cC1DLStatus )
   
   SC1->( dbSkip() ) 
  
  End While
  
 RESET ENVIRONMENT  

Return( NIL )


e, para obter a Descrição da Legenda do Pedido de Compras:

#INCLUDE "PROTHEUS.CH"
#INCLUDE "TBICONN.CH"
User Function C7LStatus()

 Local cC7DLStatus

 PREPARE ENVIRONMENT EMPRESA "01" FILIAL "01"

  ChkFile( "SC7" )
  While SC7->( !Eof() )
 
   //Obtenho a Descricao do Status
   cC7DLStatus := StaticCall( U_MT120COR , GetC7Status )
   
   //Direciono a Saida para o Console do Server
   ConOut( cC7DLStatus )
   
   SC7->( dbSkip() ) 
  
  End While
  
 RESET ENVIRONMENT  

Return( NIL )


Vale salientar que, apesar dos exemplos serem 100% funcionais eles podem deixar de vir a funcionar em versões futuras do protheus/by you pois não atentem as caracteristicas de desenvolvimento de customizações do Protheus. A totvs/microsiga poderá, a qualquer momento e sem prévio aviso e, até descaracterizando a premissa de "manter o legado", alterar as funções padrões aqui utilizadas. Então, como recomendação, utilize estes códigos apenas se extremamente necessários ou considerando-os, apenas, como exemplos didaticos.

Como sempre, para baixar a versão completa, clique aqui.

Tenho dito: "simples assim".

[]s иαldσ dj

Comentários

  1. Doideira Papai do AdvPL.

    Queria mandar um recado para o LC (Láercio Consentino), quer melhorar seu produto.

    Olha oque esse menino aqui anda fazendo!

    Totvs, atualmente está mais para TONTVS!

    ResponderExcluir
  2. Um cara da Totvs BH, chamado [x] teve uma ideia parecida. Mas nao tao bem estruturada!

    Depois lhe enviarei o codigo.

    ResponderExcluir
  3. senhores, bom dia.

    antes de mais nada parabéns pelo site. Tem me ajudado bastante.

    Necessito de filtrar as solicitações de compra utilizando duas tabelas: SC1 e Z03 onde:

    cQuery += " C1_FILIAL='"+xFilial("SC1")+"' AND C1_USER = '"+__cUserID+"' "
    //cQuery += " AND Z03_FILIAL='"+xFilial("Z03")+"' AND Z03_USER = '"+__cUserID+"' "
    //cQuery += " AND C1_CC = Z03_CC "
    //cQuery += " AND C1_USER = Z03_USER "

    Utilizei o ponto de entrada MT110QRY mas não rolou. Nem chamou.

    Utilizando o PE MT110FIL funciona mas apenas uma tabela.

    cQuery += " C1_FILIAL='"+xFilial("SC1")+"' .AND. C1_USER = '"+__cUserID+"' "

    Tem jeito?

    obrigado.

    ResponderExcluir
  4. Existem legendas que os filtros são em SQL e outras são em ADVPL eu fiz um tratamento ae funciona para qualquer tipo.

    ResponderExcluir
  5. Esse fonte ainda está funcionando, pois não está filtrando. Será que o Protheus sofreu alguma alteração que parou o funcionamento. Desde já agradeço.

    ResponderExcluir
  6. Esse fonte ainda está funcionando corretamente ou o Protheus atualizou algo que não funciona mais? Realizei os procedimentos e o mesmo não está filtrando. Desde já agradeço!!

    ResponderExcluir

Postar um comentário

Postagens mais visitadas