DataGridView: grillas paginadas
DataGridView muestra una lista de filas de una tabla en un Screen, con paginación nativa (Page Up/Down) sobre un subfile DDS. Sólo puede haber uno por Screen.
1. Ejemplo completo
@Properties {
Type : Screen
Name : SGRIDDEMO
}
@References {
Tables = ["tables/TLGRIDDEMO.warp"]
}
@Variables {
global {
VCodCli char(6)
VNombre char(20)
VCiudad char(15)
VTotal number(5)
VUltimo char(6)
}
}
@Layout {
DataGridView("GridDemo", 2, 2, 5)
[
Column("Codigo", &VCodCli)
Column("Nombre", &VNombre)
Column("Ciudad", &VCiudad)
]
}
@Source {
Event Load
For Each In GRIDDEMO Index GRIDDMNOM
&VCodCli = CodCli
&VNombre = Nombre
&VCiudad = Ciudad
LoadRow()
EndFor
EndEvent
Event Enter
&VTotal = 0
For Each Row
&VTotal = &VTotal + 1
&VUltimo = &VCodCli
EndFor
Message("Filas: " + String(&VTotal, 5) + " Ultimo: " + &VUltimo, Info)
EndEvent
}
Entre dos columnas visibles contiguas siempre queda al menos una posición libre (el separador, si se declara; si no, un espacio). Esto cuenta para el cálculo de ancho de E00353: ver Ancho disponible y error E00353.
2. Cargar la grilla: Event Load + LoadRow()
LoadRow() toma los valores actuales de las variables atadas a cada Column y agrega una fila a la grilla. Es válido en cualquier lugar del cuerpo de cualquier Event de un Screen —directo, dentro de If, Case, While, For o For Each—, de modo que también sirve para cargar la grilla con datos que no vienen de una tabla. Un For Each que cargue la grilla debe declarar Index (E00201). Puede haber varias cargas en el mismo evento: todas agregan filas a la misma grilla. En Event Load la grilla se reinicia una sola vez, al entrar al evento; en cualquier otro Event o Procedure las filas se agregan a las que ya hay. Carga todo el resultado en una sola pasada — Page Up/Down son scroll nativo del terminal sobre lo ya cargado; Load nunca vuelve a correr.
LoadRow() también se puede usar dentro de cualquier Procedure del Screen, sin importar desde dónde se invoque (con Do). Una Function no puede usar LoadRow(), ni tampoco puede usarse fuera de un Event o Procedure (E00198).
Event Load
Do Carga()
EndEvent
Procedure Carga()
For &Indice = 1 To 5
&VCod = &Indice
&VNombre = "Item " + String(&Indice, 3)
LoadRow()
EndFor
EndProc
Una Procedure con LoadRow() también puede llamarse desde otro evento. Aquí Enter agrega filas a las que Load ya cargó (y F5/Refresh vuelve a correr Load, que reinicia la grilla):
Event Enter
Do AgregaFilas()
EndEvent
Procedure AgregaFilas()
&VCod = 99
&VNombre = "Fila agregada"
LoadRow()
EndProc
Y directo en el evento, sin procedimiento ni tabla:
Event Load
&VCod = 1
&VNombre = "Primero"
LoadRow()
&VCod = 2
&VNombre = "Segundo"
LoadRow()
EndEvent
Regla relacionada: una variable local con el mismo nombre que la variable de una Column tapa a la global (LoadRow() copiaría el valor local), error E00356. Ver Diagnósticos.
3. Leer la selección: RefreshSelectRow() y CurrentInput()
Cuando el cursor cae dentro del rectángulo de la grilla (encabezado, fila de atención o cualquier fila de datos), CurrentInput() devuelve el nombre de la grilla. RefreshSelectRow() relee la fila bajo el cursor y escribe cada columna (incluidas las Hidden) de vuelta en su variable atada — es la inversa de LoadRow(). Es la forma de recuperar el valor de una columna Hidden: esas columnas viajan en el registro del subfile como campos ocultos (uso H en el DDS), sin línea ni posición en pantalla:
Event Enter
&Control = CurrentInput()
If &Control = "GridDemo"
RefreshSelectRow()
Message("Seleccionaste: " + &VCodCli, Info)
EndIf
EndEvent
4. Recorrer todas las filas cargadas: For Each Row
For Each Row ... EndFor recorre todas las filas ya cargadas en el subfile (no la tabla de base de datos), escribiendo cada Column en su variable atada antes de cada iteración — misma dirección que RefreshSelectRow(). No admite Index/Where/When None porque no hay tabla que recorrer:
Event Enter
&VTotal = 0
For Each Row
&VTotal = &VTotal + 1
EndFor
EndEvent
5. Columnas ocultas (Hidden)
Column("ID Interno", &VIdInterno, Hidden)
Una columna Hidden carga su dato (participa en LoadRow()/RefreshSelectRow()/For Each Row) pero no muestra la celda ni el título de su encabezado — útil para llevar una clave interna sin ocupar espacio en pantalla.
6. Columnas editables (Input)
Column("Cantidad", &VCantidad, Input)
Permite que el usuario edite el valor directamente en la grilla.
Recargar la grilla: Refresh y Refresh Keep
Para volver a ejecutar Event Load (por ejemplo, tras cambiar un filtro) usa Refresh (vuelve a la primera fila) o Refresh Keep (conserva la fila donde estaba el usuario). La recarga ocurre al terminar el evento actual. F5, si está declarada en @FunctionKeys, ejecuta Event Refresh y luego recarga la grilla. Ver Refresh y Refresh Keep.
7. Reglas a tener en cuenta
- El nombre (
"GridDemo") es obligatorio y único entreInput/DataGridViewde la misma pantalla. - Sólo un
DataGridViewporScreen. - Sólo válido dentro de
@Layoutde unScreen, nunca de unProgram.