Un ejemplo de un programa Harbour Qt
11/08/2010
La mejor manera de ver como funciona Qt , es con un pequeño ejemplo
*********************************************************************
* Ejemplo de uso de Qt *
*********************************************************************
#include "hbqt.ch"
#include "common.ch"
STATIC qApp
REQUEST HB_QT
INIT PROCEDURE Qt_Start()
qApp := QApplication():new()
RETURN
EXIT PROCEDURE Qt_End()
qApp:quit()
RETURN
/*----------------------------------------------------------------------*/
FUNCTION Main()
set talk off
set exclusive off
QtParamK() //Inicializa el tamaño de la pantalla en 1024x768
public oWnd, path1, dirR
HbQt_Set_Release_Method( HBQT_RELEASE_WITH_DELETE ) //Inicia entorno Qt
oWnd := QMainWindow():new() //crea contenedor Qt
oWnd : showMaximized() //Usa toda la pantalla
oWnd : setMouseTracking( .T. ) //Inicia Mouse
oWnd : setWindowTitle( Tr("Ejemplo -")) //La nombre a ventana ppl
oWnd : setWindowIcon( "../imagenes/Ksos" ) //icono de la ventana
// Ksos es un icono tipo .ico y debe estar en mi caso el subdirectorio
// imagenes imediatamente fuera de donde esta compilandose este
//ejercicio, como lo indica el path ../imagenes
MsgInfo(Tr("Bienvenido a primer ejemplo"),MSG_INFORMATIVO)
// Las tres instruciones siguientes colocan un fondo a el contendor
// principal del ejemplo , de nuevo coloacar un fondo en
// ../imagenes , totalmente cualificado , y respetando mayusculas y
// minusculas mas las extension
// setCentralWidget obliga a que la imagen use el espacio disponible
imagenPath :="../imagenes/Kactual.jpeg"
BACK:=ImagenK(oWnd, imagenPath ,,,,)
oWnd: setCentralWidGet(BACK)
//La siguiente instrucin muestra el mensaje , en la barra de
// estado y desaparece despues de 10000 milisegundos (10 segundos)
// OJO, OJO, OJO
// observece que no se lanza solo la instruccion statusK , sino que
// se asigna a SS, esto es verdad siempre, nio se pueden lanzar
// simplemente las funciones , hay que asignarlas a variables , esto
// es, porque es la forma en que se implemento en Qt, lo que se
// denomina en otros lenguajes , instancias, sino se hace asi no se
// en la pantalla lo que se esta haciendo.
// Note que el primer parametro es el nombre del contenedor de la
// apliacion Ownd, definido arriba, para que todos los objetos queden
// inscritos en el, si se usa otro, por ejemplo QLabel,QWidget, no los
// muestra automaticamtne sinio que hay que agregarlos manualmente
// mediante por ejemplo addWidget()
SS :=StatusK(oWnd,Tr("ejemplo cargado"),10000)
// Se esta usando el combo box para seleccionar el sistema operativo
// y se cooloca un mensaje de terxto indicando
// La instruccion SayK(Ownd,Y(10),X(25),TextTmp,Y(02),X(65)
// es equivalente a @ 10,25 say "Sistema operativo"
// X(10),Y(25) hacen que la presentacion sea por caracteres (ver
// funciones definidas arriba) y no por pixeles como lo usa Qt
// Los dos ultimos parametros me dicen que tan ancho y alto ,
// o que espacio ocupa el mensaje en la pantalla
// 2 caracteres de alto por 65 de ancho
// luego lleno un arreglo de 3x2 con los textos a mostrar y
// los iconos asociados, para desplegar en el combobox
// luego posiciono ek combobox en Y(10),X(50) y le doy unas
// dimensiones a ocupar, combo box regresa dos parametros
// el objeto del combo box en si mismo, y el item seleccinado
// es por esto que recojo (instancio) el combo box en una arreglo
// de dos posiciones OS, y recojo el valor seleccionado en en
// sisTmp := OS[2] , OS[1] es el objeto instanciado combobox
// cuando salgo del comobo box borro , todas las instancias que
// ya use, pues si no lo hago , quedaran siempre en la pantalla
// S0:=NIL ; OS:=NIL ; arrTmp := NIL
textTmp := Tr("Sistema operativo")
S0:=SayK(oWnd,Y(10),X(25),TextTmp,Y(02),X(65))
private arrTmp[3,2]
arrTmp[1,1] := Tr("Linux" )
arrTmp[1,2] := "../imagenes/LinuxIcon.jpeg"
arrTmp[2,1] := Tr("Windows")
arrTmp[2,2] := "../imagenes/WindowsIcon.jpeg"
arrTmp[3,1] := Tr("Mac" )
arrTmp[3,2] := "../imagenes/MacIcon.jpeg"
OS :=ComboBoxK( oWnd, Y(10),X(50),arrTmp,Y(02),X(40) )
sisTmp := OS[2]
S0:=NIL ; OS:=NIL ; arrTmp := NIL
// Aqui de acuerdo al sistema operativo elegido , asigno el tipo
// de separador adecuado y el directo de bases de datos de mi
// aplicacion
// La funcion Tr() , aun sin emplementar me da la facilidad de
// programas en cualquier idioma (ver funcion Tr() en Qt)
do case
case sisTmp = Tr("Linux")
slash := "/"
slashS:= "\"
dri:= "/home/ksos/kontable"
case sisTmp = Tr("Mac")
slash := "/"
slashS:= "\"
dri:= "/home/ksos/kontable"
case sisTmp= Tr("Windows")
slash := "\"
slashS := "/"
dri := "c:\home\ksos\kontable"
endcase
// Las siguientes instrucciones permiten modificar la ruta
// de los programas, sin embargo lo importante aqui es el uso
// exhaustivo de SayK,getK y readK
// l y dri, son solo varables de interes par mi, para posicionar
// los ojetos en la pantalla de una forma ordenada y recibir en dri,
// la ruta definitva de busqeda de las base de datos que voy a usar
// no pieradn la atencino en eso , lo mas importante ocurre en
// SI,G1,R1
// alli se instancias tres objetos:
// S1 = muesta en pantalla el mensaje "Dirtectorio de programas"
// G1 = Recibe el contenido de la variable Dri, com un get normal
// R1 = Espera hasta que el usuario le de sobre aceptar para pasar
// el valor a la variable , R1
// R1 igual que ComboBox, obtiene el objeto get y el contenidose
// selecinadao (cancelar,acaptar), en este caso solo em interesa
// capturar el cancelar, para saber si el usuario aborto la seccion
// de no ser asi, continua y asigno los valores a dri a traves de
// dri := lower(trim(G1:text))
// observe que saco el contenido instanciando G1 y leyendo el
// contenido del objeto en G1:text
// luego libero las variables Si,G1,R1
S1:=NIL ; G1:=NIL ; R1:=NIL
l := len(trim(dri))
dri:= left((trim(dri)) + space(36 - l),36)
textTmp:= Tr("Directorios de programas")
S1 :=SayK (oWnd,Y(10),X(25),textTmp ,Y(05),X(74))
G1 :=GetK (oWnd,Y(10),X(59),dri ,Y(02),X(40),len(dri),"")
G1 : setFocus()
R1 :=ReadK(oWnd,Y(12),X(59),Y(02),X(39))
if (R1[2] = "Cancelar")
quit //Si se elige cancelar sale de la apliacion
endif
dri := lower(trim(G1:text))
path1:= dri + slash + "config"
S1:=NIL ; G1:=NIL ; R1:=NIL
// las lineas siguientes hacen una presentacion del mismo modelo
// y puede observarse que el modelo es identico
duenoAux:= Tr("Dueno")
grupoAux:= Tr("Grupo")
homeAux := Tr("Path de la empresa")
S0:=SayK (oWnd,Y(08),X(25),"" ,Y(09),X(70))
S1:=SayK (oWnd,Y(08),X(25),duenoAux ,Y(02),X(30))
G1:=GetK (oWnd,Y(08),X(55),dueno ,Y(02),X(40),24,"")
G1: setFocus()
S2:=SayK (oWnd,Y(10),X(25),grupoAux ,Y(02),X(30))
G2:=GetK (oWnd,Y(10),X(55),grupo ,Y(02),X(40),24,"")
S3:=SayK (oWnd,Y(12),X(25),homeAux ,Y(02),X(30))
G3:=GetK (oWnd,Y(12),X(55),home ,Y(02),X(40),24,"")
R1:=ReadK(oWnd,Y(14),X(55),Y(02),X(39))
if (R1[2] = "Cancelar")
quit
endif
dueno:= lower(trim(G1:text))
grupo:= lower(trim(G2:text))
home := lower(trim(G3:text))
S0:=NIL ; S1:=NIL ; S2:=NIL ; S3:=NIL
G1:=NIL ; G2:=NIL ; G3:=NIL ; R1:=NIL
//Las siguientes lineas tienen un ejemplo practico como se
// puede usar el spinbox, para seleccionar un numero dado comprendido
// en un rango determinado, ene el caso que nos ocupa se selecciona
// un par de anos , donde el sistema va ser iniciado
// El spinbox, solicita los años de trabajo, el Read, mantiene
// la consulta de los valores hasta tanto el usuario confirme la
// validez de los datos o la cancelacin del proceso
// En este ejmplo se inicializa el intervalo en 10 anos anters de la
// fecha del sistema y va hasta el ano 2020
anoDes:= year(Date())-10
anoHas:= anoDes + 5
anoDAux:= Tr("Ano desde")
anoHAux:= Tr("Ano hasta")
S0:=SayK (oWnd,Y(08),X(25),"" ,Y(07),X(70))
S1:=SayK (oWnd,Y(08),X(25),anoDAux ,Y(02),X(30))
G1:=SpinK(oWnd,Y(08),X(55),year(Date()) ,Y(02),X(40),anoDes,2020,1)
G1: setFocus()
S2:=SayK (oWnd,Y(10),X(25),anoHAux ,Y(02),X(30))
G2:=SpinK(oWnd,Y(10),X(55),year(Date()) ,Y(02),X(40),anoDes,2020,1)
R1:=ReadK(oWnd,Y(12),X(55),Y(02),X(39))
if (R1[2] = "Cancelar")
quit
endif
anoDes:= G1:value
anoHas:= G2:value
S0:=NIL ; S1:=NIL ; S2:=NIL
G1:=NIL ; G2:=NIL ; R1:=NIL
//Las intruciones siguientes mantienen la validez de la informacin
// para evitar que se cree informacion no validad, toma como
// pramtros vaido 5 años, si es mayor a esto, pregunta, para verificar
// que el periodo elegido es el corecto, de lo contrario aborta el
// el proceso, en este caso se hace uso de la instruccion para el
// proposito especifico SinoK, cuyo parameto de said es "Si" o "No"
// observe la combinacion Mayuscula , minuscula.
// Tabioen verifica que la secuencia de anos sea corercta, el
// inicial menir que el final, en caso contrario lanza un mensaje
// critoco de error y cancea el proceso
if (anoHas - anoDes) > 5
textTmp:= "" + str(anoDes,4) + "-" + str(anoHas,4) + " "
textTmp:= textTmp + "" + Tr("Mas de 5 Anos") + " "
SINO=SiNoK(textTmp,0)
if SINO = Tr("No")
quit
endif
endif
if (anoHas - anoDes) < 0 textTmp:= "" + str(anoDes,4) + "-" + str(anoHas,4) + " "
textTmp:= textTmp + "" + Tr("Periodo incorrecto") + " "
MsgInfo( Tr(TextTmp),MSG_CRITICO)
quit
endif
//Y por ultimo SIEMPRE se debe concluir el programa principal con
// estas 2 instrucciones, que le dicen al sistema que ejecute todas
// las instancias, definidas en el contenedor de la aplicacion que se
// definio al inicio del programa
// con las instrucciones:
//
// STATIC qApp
//
// REQUEST HB_QT
//
// INIT PROCEDURE Qt_Start()
// qApp := QApplication():new()
// RETURN
qApp:exec()
// Estas instrucciones se efectauran cuando se cierre la aplicacion
close databses
clear
release all
return nil
***********************************************************************
* Aqui empieza el desarrollo en Qt definitvo en Harbour
*
* despues de haber intgentado con todos los otros modelos con
* resultados muy relativos
*
************************************************************************
-----------------------------------------------------------------------
La mejor manera de ver como funciona Qt , es con un pequeño ejemplo
*********************************************************************
* Ejemplo de uso de Qt *
*********************************************************************
#include "hbqt.ch"
#include "common.ch"
STATIC qApp
REQUEST HB_QT
INIT PROCEDURE Qt_Start()
qApp := QApplication():new()
RETURN
EXIT PROCEDURE Qt_End()
qApp:quit()
RETURN
/*----------------------------------------------------------------------*/
FUNCTION Main()
set talk off
set exclusive off
QtParamK() //Inicializa el tamaño de la pantalla en 1024x768
public oWnd, path1, dirR
HbQt_Set_Release_Method( HBQT_RELEASE_WITH_DELETE ) //Inicia entorno Qt
oWnd := QMainWindow():new() //crea contenedor Qt
oWnd : showMaximized() //Usa toda la pantalla
oWnd : setMouseTracking( .T. ) //Inicia Mouse
oWnd : setWindowTitle( Tr("Ejemplo -")) //La nombre a ventana ppl
oWnd : setWindowIcon( "../imagenes/Ksos" ) //icono de la ventana
// Ksos es un icono tipo .ico y debe estar en mi caso el subdirectorio
// imagenes imediatamente fuera de donde esta compilandose este
//ejercicio, como lo indica el path ../imagenes
MsgInfo(Tr("Bienvenido a primer ejemplo"),MSG_INFORMATIVO)
// Las tres instruciones siguientes colocan un fondo a el contendor
// principal del ejemplo , de nuevo coloacar un fondo en
// ../imagenes , totalmente cualificado , y respetando mayusculas y
// minusculas mas las extension
// setCentralWidget obliga a que la imagen use el espacio disponible
imagenPath :="../imagenes/Kactual.jpeg"
BACK:=ImagenK(oWnd, imagenPath ,,,,)
oWnd: setCentralWidGet(BACK)
//La siguiente instrucin muestra el mensaje , en la barra de
// estado y desaparece despues de 10000 milisegundos (10 segundos)
// OJO, OJO, OJO
// observece que no se lanza solo la instruccion statusK , sino que
// se asigna a SS, esto es verdad siempre, nio se pueden lanzar
// simplemente las funciones , hay que asignarlas a variables , esto
// es, porque es la forma en que se implemento en Qt, lo que se
// denomina en otros lenguajes , instancias, sino se hace asi no se
// en la pantalla lo que se esta haciendo.
// Note que el primer parametro es el nombre del contenedor de la
// apliacion Ownd, definido arriba, para que todos los objetos queden
// inscritos en el, si se usa otro, por ejemplo QLabel,QWidget, no los
// muestra automaticamtne sinio que hay que agregarlos manualmente
// mediante por ejemplo addWidget()
SS :=StatusK(oWnd,Tr("ejemplo cargado"),10000)
// Se esta usando el combo box para seleccionar el sistema operativo
// y se cooloca un mensaje de terxto indicando
// La instruccion SayK(Ownd,Y(10),X(25),TextTmp,Y(02),X(65)
// es equivalente a @ 10,25 say "Sistema operativo"
// X(10),Y(25) hacen que la presentacion sea por caracteres (ver
// funciones definidas arriba) y no por pixeles como lo usa Qt
// Los dos ultimos parametros me dicen que tan ancho y alto ,
// o que espacio ocupa el mensaje en la pantalla
// 2 caracteres de alto por 65 de ancho
// luego lleno un arreglo de 3x2 con los textos a mostrar y
// los iconos asociados, para desplegar en el combobox
// luego posiciono ek combobox en Y(10),X(50) y le doy unas
// dimensiones a ocupar, combo box regresa dos parametros
// el objeto del combo box en si mismo, y el item seleccinado
// es por esto que recojo (instancio) el combo box en una arreglo
// de dos posiciones OS, y recojo el valor seleccionado en en
// sisTmp := OS[2] , OS[1] es el objeto instanciado combobox
// cuando salgo del comobo box borro , todas las instancias que
// ya use, pues si no lo hago , quedaran siempre en la pantalla
// S0:=NIL ; OS:=NIL ; arrTmp := NIL
textTmp := Tr("Sistema operativo")
S0:=SayK(oWnd,Y(10),X(25),TextTmp,Y(02),X(65))
private arrTmp[3,2]
arrTmp[1,1] := Tr("Linux" )
arrTmp[1,2] := "../imagenes/LinuxIcon.jpeg"
arrTmp[2,1] := Tr("Windows")
arrTmp[2,2] := "../imagenes/WindowsIcon.jpeg"
arrTmp[3,1] := Tr("Mac" )
arrTmp[3,2] := "../imagenes/MacIcon.jpeg"
OS :=ComboBoxK( oWnd, Y(10),X(50),arrTmp,Y(02),X(40) )
sisTmp := OS[2]
S0:=NIL ; OS:=NIL ; arrTmp := NIL
// Aqui de acuerdo al sistema operativo elegido , asigno el tipo
// de separador adecuado y el directo de bases de datos de mi
// aplicacion
// La funcion Tr() , aun sin emplementar me da la facilidad de
// programas en cualquier idioma (ver funcion Tr() en Qt)
do case
case sisTmp = Tr("Linux")
slash := "/"
slashS:= "\"
dri:= "/home/ksos/kontable"
case sisTmp = Tr("Mac")
slash := "/"
slashS:= "\"
dri:= "/home/ksos/kontable"
case sisTmp= Tr("Windows")
slash := "\"
slashS := "/"
dri := "c:\home\ksos\kontable"
endcase
// Las siguientes instrucciones permiten modificar la ruta
// de los programas, sin embargo lo importante aqui es el uso
// exhaustivo de SayK,getK y readK
// l y dri, son solo varables de interes par mi, para posicionar
// los ojetos en la pantalla de una forma ordenada y recibir en dri,
// la ruta definitva de busqeda de las base de datos que voy a usar
// no pieradn la atencino en eso , lo mas importante ocurre en
// SI,G1,R1
// alli se instancias tres objetos:
// S1 = muesta en pantalla el mensaje "Dirtectorio de programas"
// G1 = Recibe el contenido de la variable Dri, com un get normal
// R1 = Espera hasta que el usuario le de sobre aceptar para pasar
// el valor a la variable , R1
// R1 igual que ComboBox, obtiene el objeto get y el contenidose
// selecinadao (cancelar,acaptar), en este caso solo em interesa
// capturar el cancelar, para saber si el usuario aborto la seccion
// de no ser asi, continua y asigno los valores a dri a traves de
// dri := lower(trim(G1:text))
// observe que saco el contenido instanciando G1 y leyendo el
// contenido del objeto en G1:text
// luego libero las variables Si,G1,R1
S1:=NIL ; G1:=NIL ; R1:=NIL
l := len(trim(dri))
dri:= left((trim(dri)) + space(36 - l),36)
textTmp:= Tr("Directorios de programas")
S1 :=SayK (oWnd,Y(10),X(25),textTmp ,Y(05),X(74))
G1 :=GetK (oWnd,Y(10),X(59),dri ,Y(02),X(40),len(dri),"")
G1 : setFocus()
R1 :=ReadK(oWnd,Y(12),X(59),Y(02),X(39))
if (R1[2] = "Cancelar")
quit //Si se elige cancelar sale de la apliacion
endif
dri := lower(trim(G1:text))
path1:= dri + slash + "config"
S1:=NIL ; G1:=NIL ; R1:=NIL
// las lineas siguientes hacen una presentacion del mismo modelo
// y puede observarse que el modelo es identico
duenoAux:= Tr("Dueno")
grupoAux:= Tr("Grupo")
homeAux := Tr("Path de la empresa")
S0:=SayK (oWnd,Y(08),X(25),"" ,Y(09),X(70))
S1:=SayK (oWnd,Y(08),X(25),duenoAux ,Y(02),X(30))
G1:=GetK (oWnd,Y(08),X(55),dueno ,Y(02),X(40),24,"")
G1: setFocus()
S2:=SayK (oWnd,Y(10),X(25),grupoAux ,Y(02),X(30))
G2:=GetK (oWnd,Y(10),X(55),grupo ,Y(02),X(40),24,"")
S3:=SayK (oWnd,Y(12),X(25),homeAux ,Y(02),X(30))
G3:=GetK (oWnd,Y(12),X(55),home ,Y(02),X(40),24,"")
R1:=ReadK(oWnd,Y(14),X(55),Y(02),X(39))
if (R1[2] = "Cancelar")
quit
endif
dueno:= lower(trim(G1:text))
grupo:= lower(trim(G2:text))
home := lower(trim(G3:text))
S0:=NIL ; S1:=NIL ; S2:=NIL ; S3:=NIL
G1:=NIL ; G2:=NIL ; G3:=NIL ; R1:=NIL
//Las siguientes lineas tienen un ejemplo practico como se
// puede usar el spinbox, para seleccionar un numero dado comprendido
// en un rango determinado, ene el caso que nos ocupa se selecciona
// un par de anos , donde el sistema va ser iniciado
// El spinbox, solicita los años de trabajo, el Read, mantiene
// la consulta de los valores hasta tanto el usuario confirme la
// validez de los datos o la cancelacin del proceso
// En este ejmplo se inicializa el intervalo en 10 anos anters de la
// fecha del sistema y va hasta el ano 2020
anoDes:= year(Date())-10
anoHas:= anoDes + 5
anoDAux:= Tr("Ano desde")
anoHAux:= Tr("Ano hasta")
S0:=SayK (oWnd,Y(08),X(25),"" ,Y(07),X(70))
S1:=SayK (oWnd,Y(08),X(25),anoDAux ,Y(02),X(30))
G1:=SpinK(oWnd,Y(08),X(55),year(Date()) ,Y(02),X(40),anoDes,2020,1)
G1: setFocus()
S2:=SayK (oWnd,Y(10),X(25),anoHAux ,Y(02),X(30))
G2:=SpinK(oWnd,Y(10),X(55),year(Date()) ,Y(02),X(40),anoDes,2020,1)
R1:=ReadK(oWnd,Y(12),X(55),Y(02),X(39))
if (R1[2] = "Cancelar")
quit
endif
anoDes:= G1:value
anoHas:= G2:value
S0:=NIL ; S1:=NIL ; S2:=NIL
G1:=NIL ; G2:=NIL ; R1:=NIL
//Las intruciones siguientes mantienen la validez de la informacin
// para evitar que se cree informacion no validad, toma como
// pramtros vaido 5 años, si es mayor a esto, pregunta, para verificar
// que el periodo elegido es el corecto, de lo contrario aborta el
// el proceso, en este caso se hace uso de la instruccion para el
// proposito especifico SinoK, cuyo parameto de said es "Si" o "No"
// observe la combinacion Mayuscula , minuscula.
// Tabioen verifica que la secuencia de anos sea corercta, el
// inicial menir que el final, en caso contrario lanza un mensaje
// critoco de error y cancea el proceso
if (anoHas - anoDes) > 5
textTmp:= "
textTmp:= textTmp + "
SINO=SiNoK(textTmp,0)
if SINO = Tr("No")
quit
endif
endif
if (anoHas - anoDes) < 0 textTmp:= "
textTmp:= textTmp + "
MsgInfo( Tr(TextTmp),MSG_CRITICO)
quit
endif
//Y por ultimo SIEMPRE se debe concluir el programa principal con
// estas 2 instrucciones, que le dicen al sistema que ejecute todas
// las instancias, definidas en el contenedor de la aplicacion que se
// definio al inicio del programa
// con las instrucciones:
//
// STATIC qApp
//
// REQUEST HB_QT
//
// INIT PROCEDURE Qt_Start()
// qApp := QApplication():new()
// RETURN
qApp:exec()
// Estas instrucciones se efectauran cuando se cierre la aplicacion
close databses
clear
release all
return nil
***********************************************************************
* Aqui empieza el desarrollo en Qt definitvo en Harbour
*
* despues de haber intgentado con todos los otros modelos con
* resultados muy relativos
*
************************************************************************
-----------------------------------------------------------------------
Atiopogist_he James Filipowski https://wakelet.com/wake/0vs2r_5rTa19GHfMQKwG2
ResponderEliminarptinveraring