Problema con Inkey y BKEYDOWN

Post Reply
User avatar
Ruben
Posts: 40
Joined: Wed Feb 20, 2008 5:40 pm
Location: Tampico,Tamps. México
Contact:

Problema con Inkey y BKEYDOWN

Post by Ruben »

Buenas tardes Antonio y Amigos del Foro, Saben tengo una duda referente a una búsqueda Tengo mi ListBox en donde tengo visualizado la lista de clientes de un dbf, en ese listbox quiero hacer una búsqueda por aproximación varios compañeros del foro me han dado sugerencias pero no he podido sacar este problemita. Quisiera que vieras el código y de favor me hicieras una sugerencia, soy principiante en la programación y pues algunas cosas que me comentan no las comprendo del todo bien, te envio el código de mi ListBox y de mis funciones.


Listbox

function BrwClientes()

local oDlg, oBrw, oBrow
local oLbx
local cVar
local n
local oDlg1
//modificar := .F.


local aHBitMaps:= { ReadBitmap( 0, "..\bitmaps\Level1.bmp" ), ; // BitMaps de 14 x 32
ReadBitmap( 0, "..\bitmaps\Level2.bmp" ), ;
ReadBitmap( 0, "..\bitmaps\Level3.bmp" ), ;
ReadBitmap( 0, "..\bitmaps\Level4.bmp" ),;
ReadBitmap( 0, "..\bitmaps\Level5.bmp" ) }

aXDts := {"5","40","30","30","5","40","13","20","12","1","3","12" }

USE Cat_cli

if RecCount() == 0
APPEND BLANK
endif

INDEX ON cat_cli->clave TO clave
SET INDEX TO clave

GO TOP

DEFINE DIALOG oDlg FROM 3, 3 TO 41, 85 TITLE "Administrador de Clientes"
@ 2, 2 SAY oSay PROMPT "Datos Generales"
@ 2, 3 say oSay Prompt "Generales" of oDlg

@ 0, 1 SAY " &LISTADO DE CLIENTES" OF oDlg
@ 10, 1 SAY " &DATOS GENERALES" OF oDlg
@ 10.5, 1.5 SAY "Clave" OF oDlg
@ 10.5, 5.5 SAY "Nombre" OF oDlg
@ 10.5, 33.5 SAY "RFC" OF oDlg
@ 12, 1.5 SAY "Calle" OF oDlg
@ 12, 22.5 SAY "Colonia" OF oDlg
@ 13.2, 1.5 SAY "Ciudad/Estado" OF oDlg
@ 13.2, 30 SAY "Código Postal" OF oDlg
@ 14.6, 1 SAY "Telefono" OF oDlg
@ 14.6, 15 SAY "Saldo" OF oDlg
@ 14.6, 23 SAY "Tipo" OF oDlg
@ 14.6, 25 SAY "Cve" OF oDlg
@ 14.6, 30 SAY "Importe" OF oDlg

@ 13, 1 get aXDts[1] OF oDlg UPDATE when .F. SIZE 20,12
//1 CLAVE
@ 13, 4 get aXDts[2] OF oDlg UPDATE when .F. SIZE 160,12
//2 NOMBRE
@ 14.5, 1 get aXDts[3] OF oDlg UPDATE when .F. SIZE
120,12 //4 CALLE
@ 14.5, 17 get aXDts[4] OF oDlg UPDATE when .F. SIZE
120,12 //5 COLONIA
@ 16, 1 get aXDts[6] OF oDlg UPDATE when .F. SIZE 160,
12 //6 CIUDAD
@ 16, 23 get aXDts[5] OF oDlg UPDATE when .F. SIZE 20,12
//7 CODIGO
@ 13, 25 get aXDts[7] OF oDlg UPDATE when .F. SIZE 52,12
//3 RFC
@ 17.5, 1 get aXDts[8] OF oDlg UPDATE when .F. SIZE
60,12 //8 TELEFONO
@ 17.5, 10 get aXDts[9] OF oDlg UPDATE when .F. SIZE
48,12 //9 SALDO
@ 17.5, 17 get aXDts[10] OF oDlg UPDATE when .F. SIZE
10,12 //10 TIPO
@ 17.5, 19 get aXDts[11] OF oDlg UPDATE when .F. SIZE
12,12 //11 CVE
@ 17.5, 22 get aXDts[12] OF oDlg UPDATE when .F. SIZE
52,12 //12 IMPORTE


@ 16, 1 SAY "Busqueda por Aproximación" OF oDlg
@ 19.5, 1 get aXDts[2] OF oDlg SIZE 160,12
oBrow:inkey:= {|nKey,nFlags| (ValidKeyClientes1(nKey,oDlg,oBrow,oGet),oBrow:Refresh())}



@ 1, 1 LISTBOX oLbx FIELDS;

alltrim( str( val( cat_cli->clave ) )), AllTrim( cat_cli->Nombre ),;
cat_cli->RFC;
HEADERS "CLAVE", "NOMBRE", "RFC";
FIELDSIZES 50, 300, 100;
ON CHANGE ( aXDts[1] := cat_cli->clave, aXDts[2] := cat_cli->Nombre, aXDts[3] := cat_cli->calle,;
aXDts[4] := cat_cli->colonia, aXDts[5] := cat_cli->codigo, aXDts[6] := cat_cli->ciudad,;
aXDts[7] := cat_cli->rfc, aXDts[8] := cat_cli->telefono, aXDts[9] := Transform(cat_cli->saldo,"999,999.99"),;
aXDts[10] := cat_cli->tipo, aXDts[11] := cat_cli->cve, aXDts[12] := Transform(cat_cli->impte,"999,999.99"),;
oDlg:Update() ) ;
SIZE 284, 137 OF oDlg



oLbx:aJustify = {.f., .f., .t.}

@ 15, 1 BUTTON "&Agregar" OF oDlg1 action cli_cap(.T.,oLbx) SIZE 40,
12
@ 15, 10 BUTTON "&Modificar" OF oDlg action cli_cap(.F., oLbx) SIZE 40,
12
@ 15, 21 BUTTON "&Borrar" OF oDlg ACTION DelClient( oLbx ) SIZE 40, 12
@ 15, 37 BUTTON "&Imprimir" OF oDlg SIZE 40, 12
//ACTION oLbx:Report( "clients Report", .t. ) ; // .t. --> wants preview
//SIZE 40, 12

@ 15, 47 BUTTON "&Salir" OF oDlg ACTION oDlg:End() SIZE 40, 12

ACTIVATE DIALOG oDlg

USE

AEval( aHBitmaps, { | hBmp | DeleteObject( hBmp ) } )

return nil



Y ESTA ES MI FUNCION

FUNCTION ValidKeyClientes1(nKey,oDlg,oBrow,oGet)
DO CASE
CASE (nKey>=48 .AND. nKey<=57) .OR. (nKey>=65 .AND. nKey<=90) .OR. nKey=8 .OR. nKey=32
IF oBrow:nColAct=1 .OR.
oBrow:nColAct=2
Select MAECLITE
IF oBrow:nColAct = 1

OrdSetFocus(1)
ELSEIF oBrow:nColAct = 2

OrdSetFocus(2)
ENDIF
DbGoTop()
IF nKey = 8

IF Len(oGet[9,2]) > 0

oGet[9,2] := Substr(oGet[9,2],1,Len(oGet[9,2])-1)

ENDIF
ELSE

oGet[9,2] += Chr(nKey)

oGet[9,1]:Refresh()
ENDIF
IF oBrow:nColAct = 1

//DbSeek(StrCeros(7,Val(oGet[9,2])))
ELSE

DbSeek(oGet[9,2])
ENDIF
ENDIF
ENDCASE
oBrow:Refresh()
RETURN


SI ME COMPILA Y NO ME MANDA NINGUN ERROR, EL DETALLE ES AL MOMENTO DE ABRIR EL LISTADO DE CLIENTES YA QUE ME ENVIA EL SIGUIENTE ERROR

Application
===========
Path and name: C:\APLICACIONES\CXC\cxc.Exe (32 bits)
Size: 1,486,848 bytes
Time from start: 0 hours 0 mins 2 secs
Error occurred at: 03/03/08, 13:22:25
Error description: Error BASE/1005 Class: 'NIL' has no property: INKEY
Args:
[ 1] = B {|| ... }

Stack Calls
===========
Called from: => _INKEY(0)
Called from: cxc.prg => BRWCLIENTES(232)
Called from: cxc.prg => (b)CREAMENU(50)
Called from: MENU.PRG => TMENU:COMMAND(0)
Called from: WINDOW.PRG => TWINDOW:COMMAND(0)
Called from: WINDOW.PRG => TWINDOW:HANDLEEVENT(0)
Called from: WINDOW.PRG => _FWH(0)
Called from: => WINRUN(0)
Called from: WINDOW.PRG => TWINDOW:ACTIVATE(0)
Called from: cxc.prg => MAIN(40)
User avatar
Antonio Linares
Site Admin
Posts: 37481
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain
Contact:

Post by Antonio Linares »

Ruben,

Aqui tienes un ejemplo simple y típico de como hacer búsquedas incrementales en un browse:

Code: Select all

#include "FiveWin.ch"

REQUEST DBFCDX

function Main()

   local oWnd, oBrw, hBmp := ReadBitmap( CurDir() + "\go.bmp" )
   local oSay, cSearch := ""

   USE ( CurDir() + "\Customer" ) VIA "DBFCDX"
   if ! File( CurDir() + "\LAST.CDX" )
      INDEX ON Customer->Last TO ( CurDir() + "\LAST" )
   endif   
   Customer->( OrdSetFocus( "LAST" ) )
   Customer->( DbGoTop() )

   DEFINE WINDOW oWnd TITLE "IncSearch"
   
   @ 1, 1 LISTBOX oBrw ;
      FIELDS hBmp, Customer->Last, Customer->First ;
      HEADERS "", "Last", "First" ;
      SIZE 220, 167
   
   oBrw:bKeyChar = { | nKey, nFlags | Search( nKey, @cSearch ), oBrw:Refresh(), oSay:Refresh() } 
   
   @ 14,  2 SAY "Searching:" SIZE 60, 30
   @ 14, 12 SAY oSay PROMPT cSearch SIZE 80, 30
   
   ACTIVATE WINDOW oWnd
   
return nil

function Search( nKey, cSearch )

   if nKey = 8 
      cSearch = SubStr( cSearch, 1, Len( cSearch ) - 1 ) 
   else 
      cSearch += Upper( Chr( nKey ) ) 
   endif
    
   Customer->( DbSeek( cSearch, .t. ) ) 

return nil
En tu código no está definida la variable oBrow, ni los browses soportan el dato Inkey. Eso es precisamente lo que te indica el error.log:

Code: Select all

oBrow:inkey := ...
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Ruben
Posts: 40
Joined: Wed Feb 20, 2008 5:40 pm
Location: Tampico,Tamps. México
Contact:

OK Antonio lo voy a probar

Post by Ruben »

Muchas gracias Antonio, lo voy adaptar a mi PRG y si tengo alguna duda te lo hare saber.


Saludos desde Mexico
User avatar
Ruben
Posts: 40
Joined: Wed Feb 20, 2008 5:40 pm
Location: Tampico,Tamps. México
Contact:

Trate de Adecuarlo pero me marca error

Post by Ruben »

Trate de adecuar la funcion que me enviaste a mi prg pero me envia el siguiente error

Error description: Error BASE/1005 Class: 'NIL' has no property: BKEYCHAR

a que se debe????

te envio el codigo con mi adecuacion


function BrwClientes()

local oBrow, nKey, oGet
local oDlg, oBrw
local oLbx
local cVar
local n
local oDlg1


local aHBitMaps:= { ReadBitmap( 0, "..\bitmaps\Level1.bmp" ), ; // BitMaps de 14 x 32
ReadBitmap( 0, "..\bitmaps\Level2.bmp" ), ;
ReadBitmap( 0, "..\bitmaps\Level3.bmp" ), ;
ReadBitmap( 0, "..\bitmaps\Level4.bmp" ),;
ReadBitmap( 0, "..\bitmaps\Level5.bmp" ) }

aXDts := {"5","40","30","30","5","40","13","20","12","1","3","12" }

USE Cat_cli

if RecCount() == 0
APPEND BLANK
endif

INDEX ON cat_cli->clave TO clave
SET INDEX TO clave

cat_cli->(OrdSetFocus("Clave"))
cat_cli->(DbGoTop())

//GO TOP

DEFINE DIALOG oDlg FROM 3, 3 TO 41, 85 TITLE "Administrador de Clientes"
@ 2, 2 SAY oSay PROMPT "Datos Generales"
@ 2, 3 say oSay Prompt "Generales" of oDlg

@ 0, 1 SAY " &LISTADO DE CLIENTES" OF oDlg
@ 10, 1 SAY " &DATOS GENERALES" OF oDlg
@ 10.5, 1.5 SAY "Clave" OF oDlg
@ 10.5, 5.5 SAY "Nombre" OF oDlg
@ 10.5, 33.5 SAY "RFC" OF oDlg
@ 12, 1.5 SAY "Calle" OF oDlg
@ 12, 22.5 SAY "Colonia" OF oDlg
@ 13.2, 1.5 SAY "Ciudad/Estado" OF oDlg
@ 13.2, 30 SAY "Código Postal" OF oDlg
@ 14.6, 1 SAY "Telefono" OF oDlg
@ 14.6, 15 SAY "Saldo" OF oDlg
@ 14.6, 23 SAY "Tipo" OF oDlg
@ 14.6, 25 SAY "Cve" OF oDlg
@ 14.6, 30 SAY "Importe" OF oDlg

@ 13, 1 get aXDts[1] OF oDlg UPDATE when .F. SIZE 20,12 //1 CLAVE
@ 13, 4 get aXDts[2] OF oDlg UPDATE when .F. SIZE 160,12 //2 NOMBRE
@ 14.5, 1 get aXDts[3] OF oDlg UPDATE when .F. SIZE 120,12 //4 CALLE
@ 14.5, 17 get aXDts[4] OF oDlg UPDATE when .F. SIZE 120,12 //5 COLONIA
@ 16, 1 get aXDts[6] OF oDlg UPDATE when .F. SIZE 160, 12 //6 CIUDAD
@ 16, 23 get aXDts[5] OF oDlg UPDATE when .F. SIZE 20,12 //7 CODIGO
@ 13, 25 get aXDts[7] OF oDlg UPDATE when .F. SIZE 52,12 //3 RFC
@ 17.5, 1 get aXDts[8] OF oDlg UPDATE when .F. SIZE 60,12 //8 TELEFONO
@ 17.5, 10 get aXDts[9] OF oDlg UPDATE when .F. SIZE 48,12 //9 SALDO
@ 17.5, 17 get aXDts[10] OF oDlg UPDATE when .F. SIZE 10,12 //10 TIPO
@ 17.5, 19 get aXDts[11] OF oDlg UPDATE when .F. SIZE 12,12 //11 CVE
@ 17.5, 22 get aXDts[12] OF oDlg UPDATE when .F. SIZE 52,12 //12 IMPORTE


//oBrow:bkeychar := {|nKey,nFlags| (ValidKeyClientes1(nkey,oDlg,oBrow,oGet),oBrow:Refresh())}
oBrw:bKeyChar = { | nKey, nFlags | Search( nKey, @cSearch ), oBrw:Refresh(), oSay:Refresh() }
@ 16, 1 SAY "Busqueda por Aproximación" OF oDlg
@ 19.5, 1 SAY oSay PROMPT cSearch SIZE 80, 30
//@ 19.5, 1 get aXDts[2] OF oDlg1 SIZE 160,12 PICTURE "@K"

@ 1, 1 LISTBOX oLbx FIELDS;
alltrim( str( val( cat_cli->clave ) )), AllTrim( cat_cli->Nombre ),;
cat_cli->RFC;
HEADERS "CLAVE", "NOMBRE", "RFC";
FIELDSIZES 50, 300, 100;
ON CHANGE ( aXDts[1] := cat_cli->clave, aXDts[2] := cat_cli->Nombre, aXDts[3] := cat_cli->calle,;
aXDts[4] := cat_cli->colonia, aXDts[5] := cat_cli->codigo, aXDts[6] := cat_cli->ciudad,;
aXDts[7] := cat_cli->rfc, aXDts[8] := cat_cli->telefono, aXDts[9] := Transform(cat_cli->saldo,"999,999.99"),;
aXDts[10] := cat_cli->tipo, aXDts[11] := cat_cli->cve, aXDts[12] := Transform(cat_cli->impte,"999,999.99"),;
oDlg:Update() ) ;
SIZE 284, 137 OF oDlg

oLbx:aJustify = {.f., .f., .t.}

@ 15, 1 BUTTON "&Agregar" OF oDlg1 action cli_cap(.T.,oLbx) SIZE 40, 12
@ 15, 10 BUTTON "&Modificar" OF oDlg action cli_cap(.F., oLbx) SIZE 40, 12
@ 15, 21 BUTTON "&Borrar" OF oDlg ACTION DelClient( oLbx ) SIZE 40, 12
@ 15, 29 BUTTON "&Buscar" OF oDlg ACTION buscar_cli(oBrow) SIZE 40, 12
@ 15, 37 BUTTON "&Imprimir" OF oDlg SIZE 40, 12
//ACTION oLbx:Report( "clients Report", .t. ) ; // .t. --> wants preview
//SIZE 40, 12

@ 15, 47 BUTTON "&Salir" OF oDlg ACTION oDlg:End() SIZE 40, 12

ACTIVATE DIALOG oDlg

USE

AEval( aHBitmaps, { | hBmp | DeleteObject( hBmp ) } )

return nil

//**********************************************************************
function Search( nKey, cSearch )

if nKey = 8
cSearch = SubStr( cSearch, 1, Len( cSearch ) - 1 )
else
cSearch += Upper( Chr( nKey ) )
endif

cat_cli->( DbSeek( cSearch, .t. ) )

return nil
User avatar
Antonio Linares
Site Admin
Posts: 37481
Joined: Thu Oct 06, 2005 5:47 pm
Location: Spain
Contact:

Post by Antonio Linares »

Ruben,

Despues de estas líneas:

@ 1, 1 LISTBOX oLbx FIELDS;
...

es cuando has de hacer:

oLbx:bKeyChar = { | nKey, nFlags | Search( nKey, @cSearch ), oLbx:Refresh(), oSay:Refresh() }

Fíjate que estabas usando oBrw en vez de oLbx. Y es al objeto oLbx al que le tienes que asignar el dato bKeyChar
regards, saludos

Antonio Linares
www.fivetechsoft.com
User avatar
Ruben
Posts: 40
Joined: Wed Feb 20, 2008 5:40 pm
Location: Tampico,Tamps. México
Contact:

Aun no funciona

Post by Ruben »

OK Antonio ya lo hice, lo coloque donde me comentaste pero no me ejecuta nada capturo una letra y no recorre la lista de nombres, no se ubica en el inicio de los nombres con esa letra



lo seguire checando
User avatar
Armando
Posts: 2479
Joined: Fri Oct 07, 2005 8:20 pm
Location: Toluca, México
Contact:

Post by Armando »

Rubén:

Este es el PROCEDURE que uso, la verdad no recuerdo quien la puso en el foro :oops: , hace tanto tiempo de eso !.

PROCEDURE Busca(cKey,oLbx,nLong)
LOCAL nSeekRec := RECNO()
DEFAULT nLong := 0
IF nLong > 0
cKey := STR(VAL(cKey),nLong,0)
ENDIF
IF GETASYNCKEY(VK_BACK)
cKey := SUBSTR(cKey,1,LEN(cKey)-1)
ENDIF
SEEK cKey SOFTSEEK
IF ! FOUND()
GO nSeekRec
ENDIF
oLbx:REFRESH()
oLbx:oVScroll:SETPOS(RECNO())
RETURN


Y el get desde donde buscas es el siguiente:

REDEFINE GET oGet VAR cBusca ID 101 OF oDlg UPDATE;
PICTURE "@!K";
ON CHANGE(SELF:ASSIGN(),;
Busca(SUBSTR(cBusca,1,SELF:nPos-1)+UPPER(CHR(nKey)),oLbx),oLbx:REFRESH());
MESSAGE "Teclee el nombre del cliente que desea localizar"

Una condición es que el archivo donde vas a buscar debe tener un indice por el campo a buscar, en mi ejemplo busco el nombre del cliente entonces tengo un índice por el nombre del cliente.

Otra condición es que el campo a buscar debe ser alfanumerico, pero con algunos pequeños ajustes al procedure se logra buscar en un campo númerico.

Saludos
SOI, s.a. de c.v.
estbucarm@gmail.com
http://www.soisa.mex.tl/
http://sqlcmd.blogspot.com/
Tel. (722) 174 44 45
Carpe diem quam minimum credula postero
User avatar
Ruben
Posts: 40
Joined: Wed Feb 20, 2008 5:40 pm
Location: Tampico,Tamps. México
Contact:

OK TKS

Post by Ruben »

OK ARMANDO TRATARE DE ADECUAR ESTE PROCEDIMIENTO A MI PRG.
CUALQUIER COSAS QUE DE TE AVISO

SALUDOS

ATTE.
RUBEN
Post Reply