c 0924494

480
AS/400e Programación con VisualAge ® para RPG Versión 4.5.1 para Windows ® SC10-3067-04 IBM

Upload: ccazorlaq

Post on 02-Jan-2016

139 views

Category:

Documents


50 download

TRANSCRIPT

Page 1: c 0924494

AS/400e™

Programación conVisualAge® para RPGVersión 4.5.1 para Windows®

SC10-3067-04

IBM

Page 2: c 0924494
Page 3: c 0924494

AS/400e™

Programación conVisualAge® para RPGVersión 4.5.1 para Windows®

SC10-3067-04

IBM

Page 4: c 0924494

ImportanteAntes de utilizar esta información y el producto al que hace referencia, asegúrese de leer la información general en “Avisos”en la página 451.

Quinta edición (Abril 2000)

Esta edición corresponde a la Versión 4, Release 5, Nivel de modificación 1, de IBM WebSphere Development Toolspara AS/400 (Programa 5769-CL3) y a todos los releases y modificaciones posteriores hasta que se indique locontrario en nuevas ediciones.

Esta edición sustituye a la publicación SC10-3067-03.

Los cambios o adiciones realizados en el texto o en las ilustraciones se indican mediante una línea vertical a laizquierda del cambio o adición.

Haga sus pedidos de publicaciones a través de su representante de IBM o de la sucursal de IBM de su localidad. Enla dirección que figura más abajo no hay existencias de publicaciones.

IBM agradece sus comentarios. Puede enviar los comentarios a:

IBM, S.A.National Language Solutions CenterAvda. Diagonal, 57108029 BarcelonaEspaña

También puede enviar sus comentarios por fax:

Desde España: 933 216 134Desde otros países: 34 933 216 134

Si tiene acceso a Internet, puede enviar sus comentarios electrónicamente a: [email protected] Consulte elapartado “Cómo enviar comentarios” en la página xi para ver una descripción de los métodos.

Cuando envía información a IBM, otorga a IBM un derecho no exclusivo de utilizar o distribuir la información decualquier manera que considere adecuada, sin incurrir en ninguna obligación hacia usted.

© Copyright International Business Machines Corporation 1994, 2000. Reservados todos los derechos.

Page 5: c 0924494

Contenido

Acerca de este manual . . . . . . . . ixA quién va dirigido este manual . . . . . . . ixPrerrequisitos e información relacionada . . . . . ixCómo utilizar este manual . . . . . . . . . ixLa biblioteca VisualAge RPG . . . . . . . . . xCómo enviar comentarios . . . . . . . . . . xiAcceso a la información en línea . . . . . . . xii

Utilización de manuales en línea . . . . . . xiiPublicaciones en formato PDF . . . . . . . xiiUtilización de ayuda en línea . . . . . . . xii

Novedades de este Release . . . . . . xv

Parte 1. Introducción a lasaplicaciones cliente/servidor . . . . 1

Capítulo 1. Creación de una aplicaciónCliente/Servidor . . . . . . . . . . . 3Acerca de la aplicación de ejemplo . . . . . . . 3Construcción de la aplicación de ejemplo . . . . . 3Decisión sobre lo que se mostrará al usuario. . . . 5

Bienvenidos al Catálogo de vídeos . . . . . . 5Examinar por categoría . . . . . . . . . . 5Búsqueda de títulos concretos . . . . . . . 6Previsualización de títulos . . . . . . . . . 6Modificación y generación de pedidos . . . . . 6Generación de pedidos . . . . . . . . . . 6

Diseño de ventanas de alto nivel . . . . . . . 6Creación de la ventana Comedy . . . . . . . . 7

Creación de la GUI . . . . . . . . . . . 7Cómo establecer los atributos . . . . . . . . 8Adición de lógica de programa . . . . . . . 9

Creación de la ventana Preview. . . . . . . . 11Creación de la GUI . . . . . . . . . . . 11Establecimiento de atributos en el momento deldiseño . . . . . . . . . . . . . . . 12Establecimiento de atributos en tiempo deejecución . . . . . . . . . . . . . . 12Adición de lógica de programa . . . . . . . 12

Creación de mensajes . . . . . . . . . . . 15Creación de la ayuda en línea . . . . . . . . 15

Ayuda según contexto . . . . . . . . . . 15Creación de pulsadores de ayuda . . . . . . 16

Repaso de la programación visual . . . . . . . 17

Capítulo 2. Planificación de laaplicación . . . . . . . . . . . . . 19Habilitación de aplicaciones seguras de Java . . . 19Decidir qué funciones se van a proporcionar . . . 19Ayuda a los usuarios . . . . . . . . . . . 19Mantener un diseño de ventana sencillo . . . . . 20

Número de ventanas . . . . . . . . . . 20Contenido de cada ventana . . . . . . . . 20

Planificar el código con eficacia. . . . . . . . 21

Mantener informados a los usuarios . . . . . . 21Utilizar un estilo coherente . . . . . . . . . 22Anticipar cuestiones de traducción . . . . . . 22

Parte 2. Cómo trabajar concomponentes . . . . . . . . . . . 23

Capítulo 3. Programación concomponentes . . . . . . . . . . . . 25Obtención y establecimiento de atributos decomponente . . . . . . . . . . . . . . 25

Referencia a componentes en el programa . . . 25Respuesta a eventos . . . . . . . . . . . 26Atributos de sistema . . . . . . . . . . . 27Cómo trabajar con atributos de evento y de sistema 27Codificación de los componentes texto estático ycampo de entrada . . . . . . . . . . . . 29

Creación y recuperación de componentes campode entrada. . . . . . . . . . . . . . 29Códigos de operación para componentes deventana. . . . . . . . . . . . . . . 30Utilización de códigos de operación de ventanaen componentes con nombres idénticos . . . . 30

Capítulo 4. Programas de ejemplo paraVisualAge RPG . . . . . . . . . . . 33Antes de empezar . . . . . . . . . . . . 34

Construcción de los ejemplos . . . . . . . 34Ejecución de los ejemplos. . . . . . . . . 34Acceso a un sistema AS/400. . . . . . . . 34

Capítulo 5. Atributos comunes . . . . 35Atributo PartName . . . . . . . . . . . . 35Atributo ParentName . . . . . . . . . . . 35Atributo PartType . . . . . . . . . . . . 35Atributos de color . . . . . . . . . . . . 37Atributo Enabled . . . . . . . . . . . . 37Atributos de tamaño y posición . . . . . . . 37Atributo Visible . . . . . . . . . . . . . 38Atributo Focus . . . . . . . . . . . . . 38Atributo UserData . . . . . . . . . . . . 39Atributo Label . . . . . . . . . . . . . 39

Sustitución de etiqueta . . . . . . . . . 39Consejos sobre la traducción. . . . . . . . 40

Capítulo 6. Utilización de transferenciade datos . . . . . . . . . . . . . . 41Una situación de transferencia de datos habitual 41Componentes que soportan la transferencia de datos 41Habilitación de componentes para la transferenciade datos . . . . . . . . . . . . . . . 41Ejemplo de transferencia de datos . . . . . . . 42

© Copyright IBM Corp. 1994, 2000 iii

Page 6: c 0924494

Capítulo 7. Utilización de componentes 45ActiveX. . . . . . . . . . . . . . . . 46

Adición de controles ActiveX . . . . . . . 47Establecimiento de propiedades . . . . . . 47Llamada a métodos. . . . . . . . . . . 48Respuesta a eventos . . . . . . . . . . 49

Control de animación . . . . . . . . . . . 50Calendario. . . . . . . . . . . . . . . 51

Determinar la fecha que el usuario haseleccionado . . . . . . . . . . . . . 51Utilizar atributos de índice de fecha . . . . . 52

Lienzo . . . . . . . . . . . . . . . . 53Recuadro de selección . . . . . . . . . . . 55

Establecimiento del estado de un componenterecuadro de selección . . . . . . . . . . 56Establecimiento de un nemotécnico . . . . . 56Señalización de eventos . . . . . . . . . 56

Recuadro de combinación . . . . . . . . . 57Selección del tipo de recuadro de combinación . 58Adición y establecimiento de la secuencia inicialde elementos . . . . . . . . . . . . . 58Adición de elementos en tiempo de ejecución . . 58Actualización de elementos de una lista . . . . 59Establecimiento del principio de la lista . . . . 59Eliminación de elementos. . . . . . . . . 59Selección y deselección de elementos . . . . . 59Recuperación de un elemento seleccionado porusuario . . . . . . . . . . . . . . . 59Utilización de claves . . . . . . . . . . 60Establecimiento del texto del campo de entrada 61Señalización de eventos . . . . . . . . . 61

Referencia a componente lógico . . . . . . . 62Referencia a atributos de componente en otroscomponentes lógicos . . . . . . . . . . 62Supervisión de eventos en otro componentelógico . . . . . . . . . . . . . . . 63

Contenedor . . . . . . . . . . . . . . 64Adición de columnas a un contenedor . . . . 64Adición de registros a un contenedor . . . . . 65Actualización de columnas de contenedor . . . 66Eliminación de registros de un contenedor . . . 67Cambio de la vista de contenedor . . . . . . 67

Cliente DDE . . . . . . . . . . . . . . 71Campo de entrada . . . . . . . . . . . . 72

Utilización del atributo InsertMode . . . . . 73Utilización del atributo Text . . . . . . . . 73Obtención y establecimiento de información parauna ventana . . . . . . . . . . . . . 73Comprobación de validez. . . . . . . . . 73Cómo evitar la entrada de datos por parte delusuario . . . . . . . . . . . . . . . 74Enmascarado de los datos confidenciales . . . 74

Gráfica . . . . . . . . . . . . . . . . 75Enviar datos al gráfico. . . . . . . . . . 75

Pulsador gráfico . . . . . . . . . . . . . 77Definición de la imagen . . . . . . . . . 78Asignación de teclas de mandato . . . . . . 78Señalización de eventos . . . . . . . . . 78

Recuadro de grupo . . . . . . . . . . . . 79Etiquetado de un recuadro de grupo . . . . . 79Agrupación de botones de selección . . . . . 79

Barra de desplazamiento horizontal . . . . . . 80Imagen . . . . . . . . . . . . . . . . 81

Creación del componente de imagen . . . . . 82Establecimiento del nombre de archivo . . . . 82Control del panel de ampliación . . . . . . 82Ejemplo de imagen . . . . . . . . . . . 83

Bean Java . . . . . . . . . . . . . . . 87Adición de beans al proyecto . . . . . . . 87Ubicación de los archivos JAR de bean . . . . 88Establecimiento de la classpath de JAR . . . . 88Establecimiento/Obtención de las propiedadesdel JavaBean e invocación de métodos . . . . 89

Recuadro de lista . . . . . . . . . . . . 90Adición y establecimiento de la secuencia inicialde elementos . . . . . . . . . . . . . 90Adición de elementos en tiempo de ejecución . . 91Actualización de elementos de una lista . . . . 91Establecimiento del principio de la lista . . . . 91Eliminación de elementos. . . . . . . . . 91Selección y deselección de elementos . . . . . 91Tipos de selección . . . . . . . . . . . 91Recuperación de elementos de la lista . . . . 92Utilización de las teclas . . . . . . . . . 92Señalización de eventos . . . . . . . . . 92Ejemplo de recuadro de lista . . . . . . . 93Ejemplo de búsqueda . . . . . . . . . . 96

Medios . . . . . . . . . . . . . . . . 99Especificación de un nombre de archivo . . . . 99Establecimiento de AudioMode . . . . . . 100Establecimiento de Volume . . . . . . . . 100Establecimiento de Position. . . . . . . . 100Utilización del componente Panel de medios 100Señalización de eventos . . . . . . . . . 100

Panel de medios . . . . . . . . . . . . 101Creación de un componente panel de medios 101Enlace con otros componentes . . . . . . . 101Señalización de eventos . . . . . . . . . 102

Barra de menús . . . . . . . . . . . . 103Creación de menús desplegables . . . . . . 103

Elemento de menú . . . . . . . . . . . 104Colocación de una marca de selección junto auna opción de menú . . . . . . . . . . 104Establecimiento del texto de menú . . . . . 104Establecimiento de un nemotécnico . . . . . 104Habilitación de elementos de menú . . . . . 105Señalización de eventos . . . . . . . . . 105

Subarchivo de mensajes . . . . . . . . . . 106Visualización de mensajes predefinidos. . . . 106Visualización de texto suministrado en elprograma. . . . . . . . . . . . . . 106Utilización de variables de sustitución . . . . 106Eliminación de mensajes. . . . . . . . . 107Ejemplo de subarchivo de mensajes . . . . . 108

Edición de múltiples líneas . . . . . . . . . 110Obtención y establecimiento del texto . . . . 110Manipulación de líneas de texto en uncomponente de edición de múltiples líneas . . 110Manipulación de caracteres en un componentede edición de múltiples líneas . . . . . . . 111Manipulación de partes seleccionadas del textoen un componente edición de múltiples líneas . 111

iv Programación con VisualAge RPG

Page 7: c 0924494

Cambio de color . . . . . . . . . . . 111Elección de fonts . . . . . . . . . . . 111Cómo evitar la entrada de datos por parte delusuario . . . . . . . . . . . . . . 111Ejemplo de edición de múltiples líneas . . . . 112

Cuaderno. . . . . . . . . . . . . . . 115Cambio del énfasis del font. . . . . . . . 115

Página de cuaderno . . . . . . . . . . . 116Mostrar el texto del separador . . . . . . . 116Establecimiento de un nemotécnico . . . . . 116

Página de cuaderno con lienzo . . . . . . . 117Interfaz ODBC/JDBC. . . . . . . . . . . 118

Conexión a una base de datos ODBC . . . . 119Creación de un conjunto de registros . . . . 119Acceso a los datos de una tabla . . . . . . 120Tipos de datos . . . . . . . . . . . . 121Recuperación de las filas de una tabla . . . . 121Actualización de los datos de una fila . . . . 122Supresión de una fila . . . . . . . . . . 122Ejemplo de componente Interfaz ODBC/JDBC 123

Recuadro de contorno . . . . . . . . . . 131Valores de altura (Height) y anchura (Width)especiales. . . . . . . . . . . . . . 131

Menú emergente . . . . . . . . . . . . 132Barra de progreso . . . . . . . . . . . . 133

Ejemplo de barra de progreso . . . . . . . 133Pulsador . . . . . . . . . . . . . . . 134

Establecimiento de un pulsador por omisión 134Establecimiento de un nemotécnico . . . . . 134Asignación de teclas de mandato . . . . . . 135Señalización de eventos . . . . . . . . . 135

Botón de selección. . . . . . . . . . . . 136Establecimiento de un nemotécnico . . . . . 136Agrupación de botones de selección . . . . . 136Establecimiento del estado de un botón deselección . . . . . . . . . . . . . . 138Señalización de eventos . . . . . . . . . 138

Graduador . . . . . . . . . . . . . . 139Obtención y establecimiento del valor delgraduador . . . . . . . . . . . . . 139Señalización de eventos . . . . . . . . . 140Ejemplo de graduador . . . . . . . . . 140

Selector cíclico . . . . . . . . . . . . . 145Establecimiento de valores del selector cíclico 145Obtención del valor del selector cíclico . . . . 146Cómo evitar la entrada de datos por parte delusuario . . . . . . . . . . . . . . 146Ejemplo de selector cíclico . . . . . . . . 146

Texto estático . . . . . . . . . . . . . 149Cambio del texto de un componente textoestático . . . . . . . . . . . . . . 149Obtención de valores de texto estático . . . . 149Obtención y establecimiento de informaciónpara una ventana . . . . . . . . . . . 150Edición de la salida . . . . . . . . . . 150

Barra de estado. . . . . . . . . . . . . 151Ejemplo de Barra de estado . . . . . . . 151

Subarchivo . . . . . . . . . . . . . . 152Creación de un componente subarchivo . . . 153Número máximo de campos por subarchivo . . 153

Códigos de operación para manipularcomponentes subarchivo . . . . . . . . 153Carga de un subarchivo . . . . . . . . . 153Determinación del tamaño de subarchivo . . . 153Obtención de la cuenta de registros . . . . . 154Lectura y actualización de registros . . . . . 154Cambio de campos de subarchivo . . . . . 154Campos ocultos . . . . . . . . . . . 155Formato de campos de subarchivo . . . . . 155Habilitación de la tabulación . . . . . . . 155Ejemplo de subarchivo . . . . . . . . . 155Señalización de eventos . . . . . . . . . 165

Submenú . . . . . . . . . . . . . . . 166Temporizador . . . . . . . . . . . . . 167

Visualización del icono Temporizador . . . . 167Establecimiento del intervalo . . . . . . . 167Generación de eventos Tick. . . . . . . . 168Obtención del valor de temporizador . . . . 168Control del temporizador utilizandomodalidades de temporizador . . . . . . . 168Ejemplo de temporizador . . . . . . . . 168

Barra de desplazamiento vertical . . . . . . . 174Ventana . . . . . . . . . . . . . . . 175Ventana con lienzo . . . . . . . . . . . 176

Visualización de una ventana . . . . . . . 176Cambio del tamaño de una ventana . . . . . 178Establecimiento del foco . . . . . . . . . 181Lista de ventanas . . . . . . . . . . . 181Terminación de un programa . . . . . . . 182Borrado de campos en una ventana . . . . . 183Ejemplo de un componente ventana . . . . . 183

*Component . . . . . . . . . . . . . . 184Utilización del componente *component . . . 184Visualizar un diálogo Abrir/Guardar como deArchivo . . . . . . . . . . . . . . 184Seleccionar una impresora . . . . . . . . 185Utilización de conectores . . . . . . . . 185

Parte 3. Cómo trabajar con datosAS/400 . . . . . . . . . . . . . . 187

Capítulo 8. Conectividad con AS/400 189Definición de la información de AS/400 . . . . 189

Consideraciones sobre el cuaderno . . . . . 189Configuración de un servidor . . . . . . . . 190

Establecimiento de un servidor en tiempo dediseño . . . . . . . . . . . . . . . 190Establecimiento de un servidor en tiempo deejecución . . . . . . . . . . . . . . 190

Utilización de áreas de datos . . . . . . . . 191Utilización de archivos de base de datos de AS/400 192

Comprobación de nivel . . . . . . . . . 196Bloqueo de archivos de base de datos deAS/400 . . . . . . . . . . . . . . 196Alteración temporal de archivos de base dedatos . . . . . . . . . . . . . . . 196

Consideraciones de E/S de base de datos deAS/400 . . . . . . . . . . . . . . . 197

Utilización de bloques de registros para mejorarel rendimiento . . . . . . . . . . . . 197

Contenido v

Page 8: c 0924494

Servidores utilizados en el AS/400 . . . . . . 198Utilización del archivo de seguridad para losapplets . . . . . . . . . . . . . . . 198

Capítulo 9. Reutilizar aplicacionesAS/400 . . . . . . . . . . . . . . 201Situación de reutilización . . . . . . . . . 201Importación de archivos de pantalla de AS/400 206

Conversión de archivos de pantalla . . . . . 207Reutilizar ayuda UIM . . . . . . . . . . 212

Funciones UIM e IPF que utilizan los mismoscódigos . . . . . . . . . . . . . . 212Funciones UIM e IPF equivalentes que utilizancódigos distintos . . . . . . . . . . . 213Funciones UIM sin equivalentes IPF . . . . . 214

Reutilizar el fuente RPG . . . . . . . . . . 214

Parte 4. Temas avanzados . . . . . 215

Capítulo 10. Depuración de laaplicación . . . . . . . . . . . . . 217Arranque del depurador. . . . . . . . . . 217Visualización del código ensamblador . . . . . 218Carga de la aparición de DLL . . . . . . . . 218Entrada de información de arranque de ladepuración . . . . . . . . . . . . . . 219Establecimiento de un punto de interrupción . . . 219Ejecución con puntos de interrupción . . . . . 221Utilización del ratón o del teclado para iniciarfunciones de depuración . . . . . . . . . 221Selección de opciones desde la barra deherramientas . . . . . . . . . . . . . 222Visualización y modificación de variables, matricesy estructuras . . . . . . . . . . . . . 223Modificación del contenido de un campo o de unaestructura . . . . . . . . . . . . . . 224Modificación de la representación . . . . . . 224Modificación de la representación por omisión . . 225Visualización de punteros y almacenamiento . . . 225Modificación de las vistas del depurador . . . . 226Establecimiento de fonts. . . . . . . . . . 227

Capítulo 11. Edición de la salida . . . 229Códigos de edición . . . . . . . . . . . 229Palabras de edición . . . . . . . . . . . 230

Partes de una palabra de edición . . . . . . 231

Capítulo 12. Utilización de archivos deimágenes, de sonido y de vídeo . . . 233Creación de iconos para Windows . . . . . . 234Conversión de iconos OS/2 a formato Windows 234

Capítulo 13. Consejos para crearayuda en línea con IPF . . . . . . . 235Creación de ayuda en línea. . . . . . . . . 235Utilización de IPF . . . . . . . . . . . . 235Soporte de ayuda para otros idiomas . . . . . 235Adición de gráficos a la ayuda en línea. . . . . 236

Decisión del tipo de ayuda que se va aproporcionar . . . . . . . . . . . . . 236

Adición de ayuda según el contexto . . . . . 236Creación de un pulsador de ayuda . . . . . 236Creación de enlaces de hipertexto . . . . . 237

Capítulo 14. Consejos para lacreación y utilización de ayudaWindows . . . . . . . . . . . . . 239Establecimiento del ID de recurso . . . . . . 240Escritura del texto de ayuda . . . . . . . . 240Creación del archivo del proyecto de ayuda . . . 241Compilación del programa VARPG . . . . . . 242Prueba de la ayuda . . . . . . . . . . . 242Creación de un archivo de contenido . . . . . 242

Capítulo 15. Consejos para lacreación de JavaHelp . . . . . . . . 243Creación de un archivo HelpSet . . . . . . . 244Creación de un archivo Map . . . . . . . . 245Creación del archivo TOC . . . . . . . . . 245Creación del archivo JAR . . . . . . . . . 246

Capítulo 16. Trabajar con mensajes 247Definición de texto para etiquetas de sustitución 247Creación de un nuevo mensaje . . . . . . . 248Edición de un mensaje . . . . . . . . . . 249Supresión de un mensaje . . . . . . . . . 249Búsqueda de un mensaje . . . . . . . . . 249Utilización de mensajes con la lógica . . . . . 250Conversión de archivos de mensajes. . . . . . 250

Cambio manual de archivos de mensajes . . . 251Utilización de mensajes y etiquetas . . . . . . 251

Capítulo 17. Comunicación entreobjetos . . . . . . . . . . . . . . 253Enlace de componentes . . . . . . . . . . 253Utilización de una aplicación VisualAge RPG comoservidor DDE . . . . . . . . . . . . . 254

AppName . . . . . . . . . . . . . 254Topic . . . . . . . . . . . . . . . 254Item . . . . . . . . . . . . . . . 254DDEAddLink . . . . . . . . . . . . 255DDEMode . . . . . . . . . . . . . 255

Comunicación entre componentes lógicos . . . . 255Realización de llamadas locales . . . . . . . 255

Utilización de la operación CALLB . . . . . 255Llamada a programas locales utilizando CALLP 258Llamada a programas locales utilizando START 259Inicio de componentes utilizando START . . . 260

Llamada a programas remotos . . . . . . . 261Llamada a programas AS/400 . . . . . . . 262Inicio de programas de estación de trabajodesde el AS/400 . . . . . . . . . . . 263

Utilización de múltiples procedimientos . . . . 264Llamadas de prototipo . . . . . . . . . 264Consideraciones sobre el procedimiento . . . 266Implicaciones del procedimiento . . . . . . 267

vi Programación con VisualAge RPG

Page 9: c 0924494

Capítulo 18. Cómo invocar métodosJava desde programas VisualAgeRPG . . . . . . . . . . . . . . . 269El tipo de datos de objeto y la palabra claveCLASS . . . . . . . . . . . . . . . 269Cómo realizar el prototipo de un método Java . . 270

Ejemplos de cómo realizar el prototipo de unmétodo Java . . . . . . . . . . . . . 271

Cómo crear objetos . . . . . . . . . . . 273Cómo invocar métodos Java . . . . . . . . 273Otras consideraciones . . . . . . . . . . 276

Capítulo 19. Consideraciones alcompilar para Java . . . . . . . . . 277Convenio de denominación del archivo deproyecto . . . . . . . . . . . . . . . 277Directivas de compilación condicional . . . . . 277Restricciones del código fuente Java . . . . . . 277Cambios posibles en el código VARPG . . . . . 278Diferencias de tiempo de ejecución . . . . . . 280Restricciones de applet . . . . . . . . . . 281Problemas de impresión de J2SDK 1.2 . . . . . 281

Capítulo 20. Llamada a funciones delsistema al compilar para Java . . . . 283Una llamada sencilla . . . . . . . . . . . 283Paso y recepción de parámetros . . . . . . . 285

Tipos de parámetro . . . . . . . . . . 285Paso de matrices . . . . . . . . . . . 306Devolución de un valor de tipo carácter . . . 322Devolución de un valor de tipo decimal conzona . . . . . . . . . . . . . . . 323Devolución de un valor de tipo empaquetado 325Devolución de un valor de tipo binario. . . . 327Devolución de un valor de tipo entero . . . . 328Devolución de un valor entero sin signo . . . 329Devolución de un valor de fecha, hora oindicación de la hora . . . . . . . . . . 331Devolución de un valor de tipo flotante . . . 331Devolución de un valor de tipo carácter delongitud variable . . . . . . . . . . . 332Devolución de valores de matriz . . . . . . 333

Capítulo 21. Cómo crear programasno GUI en VisualAge RPG . . . . . . 357Cómo crear programas VARPG autónomos . . . 357Cómo crear archivos DLL . . . . . . . . . 358Excepciones . . . . . . . . . . . . . . 361Cómo depurar aplicaciones. . . . . . . . . 361Procedimientos de depuración. . . . . . . . 361

Capítulo 22. Consideraciones sobreDBCS . . . . . . . . . . . . . . . 363Soporte de VisualAge RPG para tipos de datosDBCS . . . . . . . . . . . . . . . . 363

Tipo de datos Sólo DBCS . . . . . . . . 364Tipo de datos DBCS cualquiera . . . . . . 365Tipo de datos DBCS mixto . . . . . . . . 365Consideraciones sobre DBCS puro . . . . . 365

Capítulo 23. Fusión de código en laaplicación . . . . . . . . . . . . . 367

Capítulo 24. Conectores de proveedor 371Adición de conectores de proveedor . . . . . . 371Invocación de un conector de proveedor . . . . 371Gestión de conectores de proveedor . . . . . . 371

Capítulo 25. Creación de conectores 373Creación de conectores mediante VisualAge RPG 373

Creación del archivo .plg . . . . . . . . 373Plantilla de archivo .plg y ejemplo . . . . . 379Creación del archivo .EXE . . . . . . . . 381Empaquetado de la aplicación . . . . . . . 395

Consideraciones al crear conectores con VisualAgepara C++ . . . . . . . . . . . . . . . 395Consideraciones al crear conectores con REXX . . 395

Parte 5. Distribución de laaplicación . . . . . . . . . . . . 397

Capítulo 26. Cómo empaquetar elcódigo de tiempo de ejecución y lasaplicaciones . . . . . . . . . . . . 399Antes de empezar . . . . . . . . . . . . 399Cómo empaquetar el código de tiempo deejecución y las aplicaciones de VisualAge RPG . . 399

Inicio de la herramienta de empaquetado . . . 400Cómo empaquetar aplicaciones Windows paraWindows NT/95/98 . . . . . . . . . . 401Cómo empaquetar aplicaciones Java paraWindows NT/95/98 . . . . . . . . . . 403Cómo empaquetar aplicaciones Java para otrasplataformas . . . . . . . . . . . . . 404

Capítulo 27. Instalación del código detiempo de ejecución y lasaplicaciones para Windows NT/95/98 . 407Instalación del código de tiempo de ejecución . . 407

Nota acerca del SQL incorporado. . . . . . 407Instalación de una aplicación . . . . . . . . 407Mantenimiento del código de tiempo de ejecucióny las aplicaciones . . . . . . . . . . . . 407Instalación desde la LAN . . . . . . . . . 408Instalación silenciosa desde la LAN . . . . . . 408

Parte 6. Apéndices . . . . . . . . 411

Apéndice A. Archivos de aplicación 413

Apéndice B. Cómo escribiraplicaciones de cliente ligero . . . . 417Cómo implementar el modelo de aplicaciónVARPG ligera . . . . . . . . . . . . . 417Aplicación de ejemplo que utiliza llamadasremotas . . . . . . . . . . . . . . . 418

El programa cliente . . . . . . . . . . 419

Contenido vii

Page 10: c 0924494

El programa servidor . . . . . . . . . . 421Aplicaciones de ejemplo que utilizan colas de datos 422

La aplicación de cliente . . . . . . . . . 423El programa servidor . . . . . . . . . . 427

Otras implementaciones posibles . . . . . . . 429Ejemplo de programa servidor reutilizable . . . 429

Apéndice C. Creación y compilaciónde programas no GUI desde MS-DOS . 433Acceso a un sistema AS/400 . . . . . . . . 434

Glosario . . . . . . . . . . . . . 437

Bibliografía . . . . . . . . . . . . 449

Avisos . . . . . . . . . . . . . . 451Información de interfaz de programación . . . . 452Marcas registradas y marcas de servicio . . . . 452

Índice . . . . . . . . . . . . . . . 453

viii Programación con VisualAge RPG

Page 11: c 0924494

Acerca de este manual

Este manual es una guía para utilizar VisualAge® para RPG al objeto dedesarrollar aplicaciones cliente/servidor. Describe los pasos que tiene que seguir encada fase del ciclo de desarrollo de aplicaciones, desde el diseño al empaquetado yla distribución. Se incluyen ejemplos de programación para aclarar los conceptos yel proceso.

A quién va dirigido este manualEste manual está escrito para programadores que utilizan VisualAge RPG paradesarrollar aplicaciones cliente/servidor. En él se presupone que está familiarizadocon el desarrollo de aplicaciones RPG en sistemas AS/400®.

Prerrequisitos e información relacionadaUtilice el centro de información de AS/400 como punto de partida para consultar obuscar información técnica del AS/400. Puede acceder al Information Center desdeel CD-ROM AS/400e™ Information Center (versión en español: SK3T-1330-02(SK3T-2027-03), o desde una de las páginas Web siguientes:http://www.as400.ibm.com/infocenterhttp://publib.boulder.ibm.com/pubs/html/as400/infocenter.htm

El centro de información de AS/400 contiene temas importantes como, porejemplo, particiones lógicas, sistemas en cluster, Java, TCP/IP, servidores Web yredes seguras. También contiene enlaces de Internet a páginas Web como AS/400Online Library y AS/400 Technical Studio. En el centro de información hay unenlace que describe a grandes rasgos las diferencias de información entre el centrode información y la biblioteca en línea.

Para obtener una versión en soporte software de las publicaciones de AS/400,consulte la publicación CD-ROM AS/400e Biblioteca en soporte software, SK3T-1325-04(SK3T-0118-04).

Cómo utilizar este manual

Nota: Antes de utilizar este manual, lea Iniciación a VisualAge RPG y CODE/400. Leproporcionará una introducción rápida a VisualAge RPG.

Este manual se compone de las siguientes partes:

Introducción a las aplicaciones cliente/servidorEsta parte del manual describe los pasos que deben llevarse a cabo paracrear una aplicación cliente/servidor con VisualAge RPG. Le guía a lolargo del diseño y el desarrollo de una aplicación de ejemplo y analizacuestiones relativas al diseño de una aplicación.

Cómo trabajar con componentesEsta parte del manual contiene consejos para crear una interfaz gráfica deusuario con componentes de VisualAge RPG y escribir la lógica deprograma para controlar esos componentes. No describe cómo utilizar cadacódigo de operación ni cuáles son los detalles de cada atributo o evento.

© Copyright IBM Corp. 1994, 2000 ix

Page 12: c 0924494

Para obtener esta información, consulte los manuales VisualAge RPGManual de consulta del lenguaje y VisualAge RPG Manual de consulta decomponentes.

Cómo trabajar con datos de AS/400Esta parte del manual trata sobre cómo configurar la aplicación para poderacceder a datos en un servidor AS/400 y sobre cómo volver a utilizaraplicaciones AS/400 existentes convirtiéndolas a aplicaciones VisualAgeRPG que se ejecutan en una estación de trabajo programable (PWS).

Temas avanzadosEsta parte del manual resalta las numerosas características que puedeañadir a la aplicación VisualAge RPG. Es la sección a la que debe dirigirsesi desea información sobre temas tales como imprimir desde la aplicación,editar la salida, utilizar el depurador, utilizar archivos de imágenes ysonido, crear ayuda en línea, añadir mensajes y ejecutar la aplicación en unsistema DBCS. También describe las diversas formas en que lasaplicaciones VisualAge RPG pueden compartir datos y comunicarse.

Distribución de la aplicaciónEsta parte del manual analiza cómo empaquetar el código de tiempo deejecución de VisualAge RPG y la aplicación. También describe cómoinstalar el código de tiempo de ejecución y la aplicación en la PWS de unusuario.

La biblioteca VisualAge RPG

*Nota: Se han actualizado todas las versiones en línea de las publicaciones deWebSphere Development Tools para AS/400. Las publicaciones cuyo títuloestá marcado con un asterisco (*) no se han vuelto a imprimir en esterelease.

La biblioteca VisualAge RPG contiene las publicaciones siguientes:

*Iniciación a VisualAge RPG y CODE/400

Utilice esta publicación para familiarizarse con los conceptos y la interfaz deVisualAge RPG y como consulta de tareas al utilizar VisualAge RPG.

*Programación con VisualAge para RPG

Esta publicación contiene información específica acerca de la creación deaplicaciones con VisualAge RPG. Describe los pasos a seguir en cada fase del ciclode desarrollo de aplicaciones, desde el diseño al empaquetado y la distribución. Seincluyen ejemplos de programación para aclarar los conceptos y el proceso deldesarrollo de aplicaciones de VisualAge RPG.

*VisualAge RPG Manual de consulta de componentes

Esta publicación proporciona información sobre los componentes, atributos decomponente, eventos de componente y atributos de evento de VisualAge RPG. Esun manual de consulta para todos aquellos que desarrollan aplicaciones conVisualAge RPG.

*VisualAge RPG Manual de consulta del lenguaje

x Programación con VisualAge RPG

Page 13: c 0924494

Esta publicación proporciona información acerca del lenguaje RPG IV tal como seimplementa en el compilador VisualAge RPG. Contiene:v Conceptos básicos del lenguaje como el juego de caracteres, nombres simbólicos

y palabras reservadas, directivas del compilador e indicadores.v Tipos y formatos de datosv Manejo de errores y de excepcionesv Especificacionesv Funciones incorporadas, expresiones y códigos de operación.

Para obtener una lista de publicaciones relacionadas, consulte la bibliografía alfinal de esta publicación.

Guía de aprendizaje de VA RPG y CODE/400

Hay disponible una guía de aprendizaje en formato HTML en el URL siguiente:http://www.ibm.com/software/ad/varpg/download/#interactive

Esta guía de aprendizaje interactiva registra la evolución del usuario para podervolver fácilmente al último ejercicio realizado. Hay unas pruebas al final de cadalección que sirven de ayuda para comprobar los conocimientos adquiridos en launidad.

Nota: Para poder utilizar esta guía de aprendizaje, necesitará un navegador queadmita marcos, Java® y Javascript. También necesitará una herramienta deextracción de archivos, como WinZip, que pueda tratar nombres largos dearchivos.

También puede encontrar la información más reciente sobre VA RPG y CODE/400en la siguiente fuente en línea:

La página de presentación de VisualAge RPG y CODE/400http://www.ibm.com/software/ad/varpg/

Cómo enviar comentariosSus opiniones son importantes para ayudarnos a proporcionar la información másexacta y de la mayor calidad posible. IBM agradece todos los comentarios relativosa esta publicación o a cualquier otra documentación del AS/400.v Si prefiere enviar los comentarios por correo, puede utilizar la dirección

siguiente:

IBM S.A.National Language Solutions CenterAvda. Diagonal, 57108029 BarcelonaEspaña

Si envía una hoja de comentarios sobre la publicación desde un país que no seaEspaña, puede entregarla a la sucursal IBM local o al representante de IBM.

v Si prefiere enviar los comentarios por fax, puede utilizar el número siguiente:– Desde España: 933 216 134– Desde otros países: 34 933 216 134

v Si prefiere enviar los comentarios por correo electrónico, puede utilizar una delas direcciones siguientes:– Comentarios sobre publicaciones:

[email protected]: to toribm(torrcf)

Acerca de este manual xi

Page 14: c 0924494

– Comentarios sobre el centro de información de AS/400:[email protected]

Asegúrese de indicar lo siguiente:v El título del librov El número de la publicaciónv El número de página o el tema al que hace referencia el comentario.

Acceso a la información en líneaVisualAge RPG tiene varios manuales en línea y ayuda en línea. Puede acceder ala ayuda mientras utiliza el producto, y puede visualizar los manuales tanto siutiliza el producto como si no.

Utilización de manuales en líneaPara visualizar un manual en línea,realice una de las acciones siguientes:v Seleccione el nombre del manual desde el menú desplegable Ayuda del

Diseñador GUI de VisualAge RPG o de la ventana del editor.v Puede acceder a las publicaciones desde el menú Inicio. Seleccione Programas →

VisualAge RPG y CODE400. Después, seleccione Información de VARPG yCODE400.

Publicaciones en formato PDFTodas las publicaciones de VA RPG y CODE/400 se incluyen como parte de laayuda habitual para el producto. Además del formato normal, el producto tambiéncontiene la versión PDF de las publicaciones.

Nota: Debe disponer del programa Adobe Acrobat Reader, Versión 3.01 o superiorpara Windows, para ver el formato PDF de las publicaciones en la estaciónde trabajo. Si no dispone de dicho programa, puede descargar una copia dela página Web de Adobe Systems (http://www.adobe.com).

En la ayuda en línea están disponibles las siguientes publicaciones en formatoPDF:v Iniciación a VisualAge RPG y CODE/400v Programación con VisualAge para RPGv VisualAge RPG Manual de consulta de componentesv VisualAge RPG Manual de consulta del lenguaje

Nota: Se han actualizado todas las versiones en línea de las publicaciones deWebSphere Development Tools para AS/400.

Utilización de ayuda en líneaHay ayuda en línea disponible para todas las áreas de VisualAge RPG. Paraobtener ayuda para una ventana determinada, un recuadro de diálogo o elcuaderno de propiedades, seleccione el pulsador Ayuda (si está disponible).

Nota: Para ver la ayuda que está en formato HTML, la estación de trabajo debetener un navegador Web que soporte marcos como, por ejemplo NetscapeNavigator 4.04 o superior, o Microsoft® Internet Explorer 4.01 o superior. (Elnavegador recomendado es Netscape Navigator 4.6 o Internet Explorer 5.0)

Utilización de ayuda según el contextoPara recibir ayuda sensible al contexto en cualquier momento, pulse F1. La ayudaque aparece es específica del área de la interfaz que tiene foco de entrada. El foco

xii Programación con VisualAge RPG

Page 15: c 0924494

de entrada puede estar en elementos de menú, ventanas, recuadros de diálogo ycuadernos de propiedades, o en componentes específicos de los mismos.

Para obtener ayuda según contexto en los recuadros de diálogo, pulse el botónsobre el signo de interrogación (si está disponible) en el extremo superior derechode la ventana. Aparece un signo de interrogación al lado de la flecha del ratón.Pulse el botón sobre una palabra o un campo y aparecerá la información de ayudasobre ese determinado campo.

Utilización de hipertextoAlgunas ventanas contienen palabras, frases o gráficos que aparecen resaltados.Son enlaces de hipertexto que llevan de un tema a otro. Para visualizar ayudaespecífica de un tema resaltado, pulse en él. Cuando siga un enlace de hipertexto,puede aparecer un botón Sincronizar en la esquina superior derecha del tema deayuda. (Quizás deba retroceder páginas para verlo). Si pulsa el botón Sincronizar,la lista de temas del marco izquierdo se renueva a fin de mostrarle el lugar queocupa el tema actual en la tabla de contenido general.

Utilización de la tabla de contenido de la ayudaCuando se visualice la ventana de Ayuda, pulse el botón Sincronizar (cuando estédisponible) para visualizar la sección Componentes en el marco de la izquierda.Pulse los símbolos más + y menos − para expandir y contraer la seccióncorrespondiente al componente deseado. Para ver un tema, pulse en él.

Utilización del recurso de búsquedaEl sistema de ayuda VisualAge RPG y CODE/400 utiliza un motor de búsquedaavanzado de texto completo, que devuelve ″aciertos″ o ″coincidencias″ HTMLbasados en la petición de búsqueda. Para buscar un tema:1. Escriba una palabra, frase o pregunta (no incluya los interrogantes) en el área

de texto situada junto a las +Opciones de búsqueda. Pulse Intro.2. Si la palabra o frase no se encuentra, se visualiza información acerca del intento

de búsqueda. De lo contrario, aparece la página Resultado de la búsqueda conuna lista de temas en los que se ha encontrado la palabra o frase. Pulse elenlace que desee ver.

3. Puede utilizar las +Opciones de búsqueda para especificar el número dedocumentos que debe devolverse.

Si desea obtener consejos para refinar las búsquedas, puede ver el tema Cómobuscar información en la ayuda en línea.

Utilización de ayuda según el lenguajePara recibir ayuda según el lenguaje, pulse F1 en una ventana de edición. Si elcursor está en un código de operación, recibirá ayuda para ese código deoperación; de lo contrario, recibirá ayuda para la especificación actual.

Acerca de este manual xiii

Page 16: c 0924494

xiv Programación con VisualAge RPG

Page 17: c 0924494

Novedades de este Release

Las siguientes funciones nuevas de VisualAge RPG se han añadido en este releasede IBM VisualAge RPG y CODE (Cooperative Development Environment) paraAS/400:v Los campos de subarchivo soportan la palabra clave VALUE.v Se dispone de un nuevo atributo StartAt en el componente subarchivo. Ahora

puede forzarse que la operación READC empiece en el registro especificado.v El carácter de sustitución de etiqueta (|) se soporta ahora en las cabeceras de

columna de los subarchivos.v Puede establecerse una parada de tabulador en el componente subarchivo.v Se ha añadido la validación y formato automáticos en los campos de entrada.v Los componentes subarchivo, contenedor y recuadro de lista soportan los

eventos KeyPress y VKeyPress.v El atributo Tablabel de la página de cuaderno ahora también es de lectura.v Un nuevo atributo ShowTabs para el componente Cuaderno permite ocultar las

pestañas.v Un valor nuevo del diálogo Preferencias del usuario determina si deben

mostrarse todas las pestañas en los cuadernos de propiedades.v Se soportan posibilidades adicionales de espaciado de los componentes, en

relación con una área circundante.v El componente Lienzo ahora soporta el atributo Enabled.v El nuevo atributo de componente *component, Platform, devuelve el entorno en

el que se ejecuta la aplicación (Java o Windows).v La posibilidad de especificar el tamaño y la posición de un componente dentro

de una ventana.v La posibilidad de invocar mandatos de usuario en el último paso de

construcción.v La ayuda en línea se visualiza ahora en formato HTML. (Deberá tener instalado

un navegador en la estación de trabajo para ver la ayuda).v Se da soporte a Personal Communications (PCOMM) para Windows.v Un nuevo diálogo ’Señas de identidad’ del Diseñador GUI proporciona

información sobre el proyecto y VARPG.v Se ha añadido el nuevo componente Bean Java a la paleta de componentes.

Ahora pueden utilizarse componentes JavaBean en la aplicación.v Las opciones de menú dan soporte a la ayuda ¿Qué es esto? en las aplicaciones

Java.v Los componentes Campo de entrada y Edición de múltiples líneas proporcionan

un nuevo valor que conserva la selección de texto aunque la ventana en la queestán pierda el foco.

v Se ha añadido un botón Buscar en el diálogo Empaquetar componente.v Para cada proyecto puede especificarse el directorio TEST.

© Copyright IBM Corp. 1994, 2000 xv

Page 18: c 0924494

xvi Programación con VisualAge RPG

Page 19: c 0924494

Parte 1. Introducción a las aplicaciones cliente/servidor“Capítulo 1. Creación de una aplicación Cliente/Servidor” en la página 3

Le guía a lo largo del diseño y la implantación de una aplicacióncliente/servidor.

“Capítulo 2. Planificación de la aplicación” en la página 19Le ayuda a planear y diseñar una interfaz gráfica de usuario para la nuevaaplicación cliente/servidor.

© Copyright IBM Corp. 1994, 2000 1

Page 20: c 0924494

2 Programación con VisualAge RPG

Page 21: c 0924494

Capítulo 1. Creación de una aplicación Cliente/Servidor

Este capítulo describe cómo crear una aplicación cliente/servidor utilizandoVisualAge® RPG. Se utiliza una aplicación de ejemplo para describir las fasessiguientes del proceso de desarrollo:1. Diseño de lo que el usuario verá y hará con la aplicación.2. Creación de la interfaz gráfica de usuario (GUI).3. Establecimiento de atributos para los componentes de la GUI.4. Escritura de la lógica de programa para controlar la GUI.5. Escritura de los mensajes y la ayuda en línea para la aplicación.

Acerca de la aplicación de ejemploLa aplicación de ejemplo, denominada Video Store Catalog, se creó con VisualAgeRPG y se encuentra en la carpeta Aplicaciones de ejemplo de VisualAge RPG.Proporciona un catálogo en línea que los clientes pueden utilizar para comprarvídeos y tiene un componente lógico de visualización previa que permite a losclientes ver secuencias del vídeo antes de hacer el pedido.

La información acerca de los vídeos está almacenada en una base de datos en elsistema AS/400®. Los clientes que utilizan el Video Store Catalog (Catálogo devídeos) están viendo en realidad los datos almacenados en el sistema AS/400. Lainformación que proporcionan los clientes, como su nombre y su número deteléfono, también se almacena en el sistema principal.

Nota: El Cajero de vídeo-club, otra aplicación de ejemplo, accede a la misma basede datos del sistema principal. Utiliza la información de los pedidos de losclientes para actualizar el inventario de la tienda y para facturar a losclientes. El Cajero de vídeo-club no se analiza en este capítulo. Para obtenerinformación acerca de su construcción y ejecución, vea los comentarios en elarchivo CASHIER.VPG en la carpeta del proyecto Cajero de vídeo-club.

Construcción de la aplicación de ejemploLa aplicación Video Store Catalog requiere que los archivos que se definen en laespecificación F se hallen presentes en un sistema AS/400. El subdirectorioadtswin\samples\vidcust tiene el archivo de salvar VIDEOSTORE.sav de la bibliotecacon los archivos necesarios.

Para subir los archivos necesarios y crear la aplicación y su componente asociadode visualización previa, siga los pasos que se indican a continuación:1. Asegúrese de que tanto VisualAge RPG como los ejemplos de VisualAge RPG

estén instalados. Si desea más información, consulte la publicación Instalación deVisualAge RPG y CODE/400 para AS/400.

2. Suba el archivo VIDEOSTORE.sav y restáurelo en el sistema AS/400 tal comose indica a continuación:a. En el sistema AS/400, cree un archivo de salvar denominado VIDEOSTORE

en cualquier biblioteca como, por ejemplo, USER.b. En la estación de trabajo, cambie el directorio actual por el de vidcust y

emita el siguiente mandato FTP:c:\adtswin\samples\vidcust>ftp HOSTNAME

© Copyright IBM Corp. 1994, 2000 3

Page 22: c 0924494

c: es la unidad en la que ha instalado el producto y HOSTNAME es elnombre del sistema AS/400 en el que ha creado el archivo de salvar. (Enlugar del nombre, puede utilizar la dirección TCP/IP del AS/400).

c. Entre el ID de usuario del AS/400 cuando así se lo solicite.d. Entre la contraseña cuando así se lo solicite.e. Una vez haya iniciado la sesión, haga que USER sea la biblioteca actual.

Entre:ftp>cd user

f. Especifique una transferencia binaria de archivos. Entre:ftp>binary

Aparecerá el mensaje 200 Representation type is binary IMAGE.g. Transfiera el archivo de salvar. Entre:

ftp>put VIDEOSTORE.sav

El mensaje File transfer completed successfully. indica que se ha subido elarchivo VIDEOSTORE.sav.

h. Entre: ftp>quitEl archivo de salvar VIDEOSTORE debe estar ahora en la biblioteca USERdel sistema AS/400.

i. Utilice el mandato RSTLIB para restaurar la biblioteca y conservar el mismonombre, VIDEOSTORE, en el sistema AS/400. De lo contrario, cambie elparámetro REMOTE_FILE_NAME del archivo Catalog.rst por el nombre conel que ha restaurado el archivo de salvar.

j. En el archivo Catalog.rst file, cambie el parámetroREMOTE_LOCATION_NAME de modo que apunte al nombre de laubicación remota del sistema AS/400.

3. Cree la aplicación de ejemplo Video Store Catalog. SeleccioneConstruir>Windows NT/95/98 o Construir>Java en el menú emergente de lacarpeta del proyecto Video Store Catalog de la carpeta Proyectos de ejemplo deVisualAge RPG. Cuando se construye satisfactoriamente el proyecto, se crea unprograma ejecutable, CATALOG.EXE para Windows, o CATLAOG.CLASS paraJava, en la carpeta del proyecto Video Store Catalog.

4. Construya el componente Preview asociado. Seleccione Construir>WindowsNT/95/98 o Construir>Java en el menú emergente de la carpeta del proyectoPreview. Cuando el proyecto se construye satisfactoriamente, se crea unabiblioteca de enlace dinámico (COMMON.DLL) para Windows, o bien unarchivo COMMON.CLASS para Java.

Utilice uno de los métodos siguientes para ejecutar la aplicación Catálogo devídeos:v Seleccione Ejecutar>Windows NT/95/98 o Ejecutar>Java en el menú emergente

de la carpeta del proyecto Video Store Catalog.v Abra la carpeta de proyecto Catálogo de vídeos y efectúe una doble pulsación

en el icono CATALOG.EXE.v Escriba catalog en una línea de mandatos.

Notas:

1. Los aspectos multimedia de esta aplicación requieren un hardware y unsoftware adicionales. Para ejecutar el audio en la previsualización, debe teneruna tarjeta de sonido en el sistema. Para ejecutar la secuencia de vídeo en laprevisualización, debe tener instalado Media Player. Las aplicaciones Javadeben tener instalada la API JMF (Java Media Framework).

2. Las secuencias de vídeo son archivos ·AVI (para Windows) o bien ·MOV (paraJava) que están almacenados en la carpeta Preview.

4 Programación con VisualAge RPG

Page 23: c 0924494

3. Para construir y ejecutar aplicaciones Java, debe tener instalado el Java 2Software Development Kit (J2SDK) Versión 1.2, o superior, de Sun, en laestación de trabajo. Si no tiene el J2SDK, puede bajarlo de Sun Microsystems enel URL siguiente:http://www.javasoft.com/products/

Tras instalar el J2SDK, establezca la variable de entorno PATH de modo queapunte a la ubicación tanto del compilador Java como del Java RuntimeEnvironment (JRE). Por ejemplo, si el directorio inicial de J2SDK es c:\jdk1.2,añada la siguiente sentencia en la variable PATH: c:\jdk1.2\bin

Decisión sobre lo que se mostrará al usuarioUn paso clave al crear la aplicación es el de decidir qué desea que haga el usuariocon la aplicación, y luego determinar lo que le tiene que proporcionar en laaplicación para que pueda realizarlo.

Durante las fases de planificación de la aplicación Catálogo de vídeos, se hadecidido que los clientes deberían poder listar los vídeos de un tipo en particular(como Action/Adventure o Comedy). También deben poder listar los vídeosrealizados por su director favorito, los protagonizados por su actor preferido, o losque están entre los 10 más vendidos en la tienda. Para ayudarles a decidir sidesean comprar un vídeo en particular o no, deben poder tener unaprevisualización del mismo. Una vez que han encontrado el vídeo que deseancomprar, pueden hacer su pedido y pagar la compra en el mostrador de caja.

Ahora que hemos identificado lo que los clientes deben poder hacer con laaplicación, podemos diseñar lo que verán cuando visualicen el catálogo de vídeos.Éste es el momento de empezar a diseñar el contenido, el número y el orden de lasventanas de la aplicación.

Bienvenidos al Catálogo de vídeosLa ventana principal, o punto de entrada de la aplicación, es la ventana VideoCatalog — Welcome. Define lo que los clientes pueden hacer con el catálogo. Parautilizar el catálogo, los clientes deben accionar un pulsador gráfico para seleccionarentre las opciones siguientes:

Browse by Category...

New releases...

Top 10 Best Sellers...

Search for Specific Titles...

Help Catalog

Al seleccionar Help Catalog se visualiza la ventana Get Help on using the Catalog. Siacciona uno de los otros pulsadores, se visualiza otra ventana desde la que podrárealizar otras acciones, tales como ver listas, previsualizar secuencias del vídeo ogenerar un pedido de compra.

Examinar por categoríaAl seleccionar Browe by Category, se visualiza la ventana Video Catalog —Categories. Esta ventana presenta una lista de categorías de vídeos en la que puedeelegirse una:

Capítulo 1. Creación de una aplicación Cliente/Servidor 5

Page 24: c 0924494

Action/Adventure HorrorChildren WesternScience Fiction RomanceComedy Classics

Para seleccionar una categoría, el cliente acciona su pulsador asociado. Esto haceque se visualice la ventana Video Titles, que lista los títulos de esa categoría. Losclientes pueden visualizar previamente algunos de los títulos, añadir un título a supedido, suprimirlo del pedido si han cambiado de opinión, y someter su pedido alcajero.

Búsqueda de títulos concretosLa ventana Video Catalog — Search permite a los clientes buscar un vídeo segúnsu categoría, título, director o actor. Tras especificar los criterios de búsqueda yaccionar el pulsador Search para iniciar una búsqueda en la base de datos deAS/400, el resultado se visualiza en la ventana Video Titles.

Previsualización de títulosLos clientes pueden tener información previa de un vídeo que está en la listaleyendo un resumen del mismo o, si tienen el hardware y el software apropiados,pueden ver una secuencia del vídeo con el audio asociado.

Modificación y generación de pedidosLa ventana Video Catalog — Review/Order My Selections permite a los clientesmodificar sus pedidos. Pueden suprimir vídeos de la lista, cambiar el número decopias que desean comprar y cambiar el tipo de soporte en el que desean que esté(cinta o disco láser). Esta ventana se visualiza cuando los clientes seleccionan unvídeo de una lista en una ventana Video Titles y accionan el pulsadorReview/submit order.

Una vez entrada toda la información para su pedido, los clientes pueden sometersu pedido desde esta ventana.

Generación de pedidosCuando los clientes generan sus pedidos, deben proporcionar su nombre, direccióny número telefónico en la ventana Video Catalog — Order Reference. Estainformación se almacena en una base de datos en el AS/400.

Diseño de ventanas de alto nivelAnalizar cómo crear cada una de las ventanas del Catálogo de vídeos está fueradel ámbito de este capítulo. Las secciones siguientes describen cómo podría utilizarel Diseñador GUI para crear dos ventanas que se parezcan a las ventanas Comedyy Preview, modificar algunos de sus atributos de componente y escribir una partede la lógica de programa asociada. Encontrará estas ventanas a lo largo de laaplicación Catálogo de vídeos:

Video Catalog — Welcome Al accionar el pulsador Browse by Category en laventana Video Catalog — Welcome se visualiza laventana Video Catalog — Categories.

6 Programación con VisualAge RPG

Page 25: c 0924494

Video Catalog — Categories Al accionar el pulsador Comedy en la ventana VideoCatalog — Categories se visualiza la ventana VideoCatalog — Comedy.

Video Catalog — Comedy Al pulsar el botón Preview después de seleccionar untítulo en la ventana Video Catalog — Comedy sevisualiza una ventana Preview.

Video Catalog — Preview La previsualización se ejecuta en esta ventana.

Si desea ver el diseño de la aplicación de ejemplo, seleccione Editar en el menúemergente de la carpeta del proyecto Video Store Catalog en la carpeta Proyectosde ejemplo de VisualAge RPG. Esta acción visualiza la ventana de proyecto de laaplicación y la paleta de componentes. La ventana de proyecto muestra todas lasventanas definidas en la aplicación. Efectúe una doble pulsación en cualquierentrada para ver su ventana de diseño con los componentes asociados. Para ver elcódigo fuente VARPG del proyecto, seleccione Proyecto>Editar código fuente en laventana del proyecto.

Creación de la ventana Comedy

La ventana Comedy visualiza la lista de vídeos de comedias que los clientespueden adquirir. Esta sección describe cómo puede crear una ventana que separezca a ésta.

Creación de la GUISeleccione una ventana con componente lienzo desde la paleta de componentescon el botón derecho del ratón, mueva el icono del puntero sobre la vista deproyecto del Diseñador GUI, y vuelva a pulsar el botón derecho del ratón. Seconvierte en la ventana de diseño, en la que situará los siguientes componentes dela paleta: recuadro de grupo, pulsador, texto estático y subarchivo.

Figura 1. La ventana Comedy

Capítulo 1. Creación de una aplicación Cliente/Servidor 7

Page 26: c 0924494

Alineación de los componentesPuede utilizar las herramientas de alineación del Diseñador GUI para definir eltamaño, la alineación y los espacios de los componentes de forma que se parezcana los que se muestran en la Figura 1 en la página 7. Si desea obtener informaciónsobre la utilización de estas herramientas, puede consultar la ayuda en línea o eltutorial HTML.

Cómo establecer los atributosDespués de colocar y posicionar un componente en la ventana, puede modificarlos valores por omisión para los atributos del componente mediante los cuadernosde propiedades. Para hacerlo, pulse con el botón derecho del ratón en elcomponente y seleccione Propiedades en el menú emergente del componente.

Algunos atributos de componente que puede modificar se describen más adelante.

Atributos de ventanaPuede seleccionar los elementos que desea que aparezcan en la ventana (talescomo el menú del sistema, la barra de título y los botones de minimizar ymaximizar) y configurar el borde de la ventana. Por omisión, la ventana utiliza elfont del sistema y tiene un fondo blanco. Puede cambiar el font y el color.

Atributos de lienzoPor omisión, el componente lienzo utiliza el font del sistema, y el fondo es elmismo que el de la carpeta. Puede cambiar el font y el color de fondo delcomponente lienzo. También puede colocar un gráfico en el componente lienzo.

Atributos de subarchivoPor omisión, el componente subarchivo se crea sin columnas. Si conoce losnombres de campo de base de datos, puede crear campos de entrada desubarchivo mediante el Diseñador GUI. De lo contrario, puede hacer referencia alos campos existentes en la base de datos de AS/400 siguiendo estos pasos:1. Seleccione Definir campos de referencia del menú Servidor. Aparece la

ventana Definir campos de referencia.2. Especifique la información de AS/400 y biblioteca para ver la información de

campos de base de datos.3. Seleccione los campos adecuados del recuadro de lista Campos con el botón

derecho del ratón, mueva el icono del puntero sobre el componente subarchivode la ventana de diseño, y vuelva a pulsar el botón derecho del ratón.El nuevo campo de entrada de subarchivo hereda los atributos del campooriginal: Length se establece en la anchura de columna y Type en el tipo dedatos.

Establezca el estilo y el tipo de datos para un campo de entrada de subarchivomediante el cuaderno de propiedades adecuado. Por ejemplo, puede establecer lalongitud o el tipo de datos.

Atributos de pulsadorEtiquete cada uno de los pulsadores para indicar al usuario la finalidad delpulsador. Para crear un carácter nemotécnico para cada pulsador, coloque elidentificador del nemotécnico antes de dicho carácter en la etiqueta. En WindowsNT, utilice el símbolo &. Observe que se han puesto unos puntos suspensivos ( ... )en la etiqueta del pulsador Review/submit order con el fin de que los usuariossepan que deben proporcionar más información después de pulsar el botón paragenerar el pedido.

8 Programación con VisualAge RPG

Page 27: c 0924494

Para cada pulsador, especifique qué acción se producirá cuando un usuario loaccione. Por ejemplo, para el pulsador Preview se realizará una subrutina deacción; para el pulsador Help, se visualizará ayuda para la ventana. Puedeestablecer esta información en el separador Acción del cuaderno de propiedadesdel pulsador. (Consulte “Creación de la ayuda en línea” en la página 15 paraobtener información relacionada.)

Adición de lógica de programaSe requiere lógica de programa para dirigir ciertas funciones GUI. Esta seccióndescribe una parte de la lógica de programa de Catálogo de vídeos. (El archivofuente, VisualAge RPG, está en la carpeta Catálogo de vídeos.)

Nota: Puede escribir la lógica de programa para un evento en particular invocandouna sesión de edición del Diseñador GUI. Por ejemplo, para añadir lógica deprograma al evento Press para un pulsador en particular, seleccioneEventos→Press del menú emergente del pulsador.

Visualización de la ventana ComedyPara hacer que la ventana Comedy aparezca cuando el usuario acciona el pulsadorComedy en la ventana Video Titles — Categories, puede hacer lo siguiente:1. Escribir una subrutina de acción para manejar el evento Press para el pulsador

Comedy.Se ha escrito la subrutina de acción COMEDYGPB (que se muestra en laFigura 2) para manejar este evento. Cuando el usuario acciona el pulsador, lasubrutina COMEDYGPB llama a la subrutina de usuario brComedy. Estasubrutina lee la base de datos de AS/400 y llama a otra subrutina de usuario,dspbrowse, para comprobar si la base de datos está vacía. Si está vacía, sevisualiza un mensaje. Si no está vacía, el control vuelve a la subrutina deusuario brComedy, el título de la ventana cambia y se visualiza el resultado dela búsqueda de la base de datos.

2. Escriba la lógica de programa para leer los títulos de vídeos de comedia de labase de datos de AS/400 y rellene el componente subarchivo con la lista detítulos. Llame a la subrutina dspbrowse para comprobar si la base de datos estávacía o no. Si la base de datos no está vacía, establezca el título de la ventanade examinar para que visualice los títulos de comedias encontrados. De locontrario, visualice el número de mensaje MSG0001 para informar al usuario deque no se ha encontrado ninguna coincidencia en la base de datos. ConsulteFigura 3 en la página 10.

*********************************************************************** **** Subrutinas de enlace de acción de la ventana de categorías **** **** ************************************************************************* Esta rutina se ejecuta cuando se acciona el pulsador del gráfico Comedy de* la ventana de categorías.*

C COMEDYGPB BEGACT PRESS CATWC z-add 0 srchdirC z-add 0 srchactC exsr brComedyC ENDACT

Figura 2. Manejo del evento PRESS

Capítulo 1. Creación de una aplicación Cliente/Servidor 9

Page 28: c 0924494

Visualización de la ventana PreviewSe ha escrito una subrutina de acción (consulte Figura 4 en la página 11) see paramanejar el evento PRESS para el pulsador Preview en la ventana Comedy. Cuandoel usuario acciona el pulsador, se llama a la subrutina de acción PREVIEWPB parainiciar el componente lógico común que visualiza la ventana Preview.

********************************************************************** ** Subrutina de usuario: brComedy ** Descripción : Mostrar ventana Browse con vídeo Comedy ** **********************************************************************

C brComedy BEGSRC clear browsesf* Obtener registros de vil0004, el archivo lógico en el AS/400* para vídeos de tipo Comedy.

C *start setll vil0004C read vil0004 61C *IN61 doweq '0'C exsr ckcriteriaC read vil0004 61C endC exsr dspbrowse* Las siguientes tres líneas definen el texto de la barra de título de* la ventana Browse.

C movel *blanks vdocatstlC movel stlcmdy vdocatstlC eval %setatr('browsew':'browsew':'Label') =C vdocatttlC ENDSR

...

********************************************************************** ** Subrutina de usuario: dspbrowse ** Descripción : Comprobar si el subarchivo de examinar está ** vacío. Si es así, mostrar mensaje MSG00001. ** **********************************************************************

C dspbrowse BEGSRC eval items=%getatr('BROWSEW':'BROWSESF':'Count')C items ifeq 0C *MSG0001 dsply msgrsp 9 0C elseC eval %setatr('BROWSEW': 'BROWSEW': 'VISIBLE')=1C eval %setatr('BROWSEW': 'BROWSEW': 'FOCUS')=1C endifC ENDSR

Figura 3. Lectura de la base de datos AS/400 y visualización de la ventana Resultados

10 Programación con VisualAge RPG

Page 29: c 0924494

Creación de la ventana Preview

La ventana Preview utiliza las posibilidades multimedia del sistema operativo paraproporcionar a los clientes una visualización breve de una secuencia del vídeo.Esta sección describe cómo puede crear una ventana que se parezca a ésta.

Nota: Para ejecutar el audio en la previsualización, debe tener una tarjeta desonido en el sistema. Para ejecutar la secuencia de vídeo, debe tenerinstalado Media Player. Las aplicaciones Java deben tener instalada la APIJMF (Java Media Framework).

Creación de la GUISeñale y pulse los siguientes componentes a un componente ventana con lienzopara crear una ventana que se parezca a la ventana Preview:v Componente mediosv Componente edición de múltiples líneasv Componentes pulsadorv Componentes texto estático

********************************************************************** Cuando se selecciona el pulsador Preview de la ventana Browse, se inicia* el componente común. Este componente muestra la ventana Preview* de un vídeo.**

C PREVIEWPB BEGACT PRESS BROWSEWC READS BROWSESF 55C *IN55 ifeq '0'C start 'common'C parm brsfpartC endifC ENDACT

Figura 4. Subrutina de acción para visualizar la ventana Preview

Figura 5. La ventana Preview

Capítulo 1. Creación de una aplicación Cliente/Servidor 11

Page 30: c 0924494

Establecimiento de atributos en el momento del diseñoDespués de colocar y situar los componentes en la ventana, puede establecer losatributos de componente mediante los cuadernos de propiedades respectivos.Algunos de los atributos que pueden establecerse están descritos más adelante.

Atributos del componente mediosLos componentes pulsador se utilizan para controlar la reproducción de lasecuencia de vídeo: Play (Reproducir), Pause (Pausa), Record (Grabar) y Stop(Detener). El atributo AudioMode establece la modalidad de operación delcomponente medios.

Atributos de texto estáticoPuede cambiar el atributo de font de un componente texto estático para quedestaque del resto de texto en la pantalla. Cambie el tamaño del componente textoestático de manera que sea lo bastante grande para contener el texto más largo. (Esaconsejable dejar un poco de espacio adicional por si se traduce la aplicación en elfuturo).

Componente edición de múltiples líneasEn el código establecemos el componente edición de múltiples líneas (MLE)denominado ABSTMLE para aceptar texto. En el cuaderno de propiedades delcomponente, se ha indicado que el componente es de sólo lectura.

Establecimiento de atributos en tiempo de ejecuciónPara cambiar el título de la ventana visualizada en tiempo de ejecución, hemosutilizado el código de operación SETATR para establecer el atributo Label (vea laFigura 6 en la página 13).

Adición de lógica de programaTiene que proporcionar una parte de la lógica de programa para controlar ciertasfunciones GUI en la ventana Preview. Esta sección describe parte de la lógica deprograma (vea la Figura 6 en la página 13) para el componente lógico Preview.

Especificación de vídeo para su previsualizaciónEl vídeo seleccionado en la ventana Comedy determina qué previsualización devídeo se reproduce. La subrutina de acción previeww lee qué vídeo va a utilizarsey luego determina el nombre del archivo de vídeo propiamente dicho.

Control del vídeoPuede escribir código para controlar el vídeo utilizando el componente medios. Ennuestro ejemplo, el componente medios se utiliza para reproducir un archivo devídeo digital asociado al vídeo seleccionado.

Los pulsadores con el atributo AudioMode asociado controlan la reproducción delarchivo de vídeo:

1 Pausa

2 Reproducir

3 Grabar

4 Parar

A continuación encontrará el código para el componente Preview:

12 Programación con VisualAge RPG

Page 31: c 0924494

**********************************************************************

Fvideo if e k disk remote BLOCK(*YES)*

DFlg s 1 inz(*OFF)DFldx s 12***********************************************************************

C *entry PLISTC parm partno 5 0*********************************************************************** Subrutinas de enlace de acción para PREVIEWW ***********************************************************************

C PREVIEWW BEGACT CREATE PREVIEWWC partno setll video 50C N50*msg0001 DSPLY msgrsp 9 0C read video 51C *IN51 IFEQ '0'C 'TITLEST' SETATR vititle 'label'C 'DIRST' SETATR vidirect 'label'*

C viactr1 CAT viactr2:1 actors 41C 'ACTST' SETATR actors 'label'*

C 'ABSTMLE' SETATR vireview 'text'** Si es para Java, utilizar el archivo .mov/If defined(COMPILE_JAVA)*

C vibitmap CAT '.mov':0 videofil 13* Si no es para Java, utilizar el archivo .avi/else

C vibitmap CAT '.avi':0 videofil 13/EndIf

C endif*significa que videofil no se ha cargado todavía en Audio

C move 'N' loaded*

C ENDACT* *

Figura 6. El componente Preview (Pieza 1 de 2)

Capítulo 1. Creación de una aplicación Cliente/Servidor 13

Page 32: c 0924494

**********************************************************************

C PBPLAY BEGACT PRESS PREVIEWW*

C if loaded='N'C eval %setatr('previeww':'audo':'FileName')C =videofilC move 'Y' loaded 1C endif*

C eval %setatr('previeww':'audo':'audioMode')=2*

C ENDACT* ***********************************************************************

C PBPAUSE BEGACT PRESS PREVIEWW*

C eval %setatr('previeww':'audo':'audioMode')=1C ENDACT* ***********************************************************************

C PBRECORD BEGACT PRESS PREVIEWW*

C eval %setatr('previeww':'audo':'audioMode')=3C ENDACT

* ***********************************************************************

C PBSTOP BEGACT PRESS PREVIEWW*

C eval %setatr('previeww':'audo':'audioMode')=4C ENDACT* ***********************************************************************

C CANCELPB BEGACT PRESS PREVIEWW*

C move *on FlgC STOPC ENDACT* ***********************************************************************

C PREVIEWW BEGACT CLOSE PREVIEWW*

C if Flg=*ONC eval Fldx='*DEFAULT'C elseC eval Fldx='*NODEFAULT'C endifC ENDACT Fldx*

Figura 6. El componente Preview (Pieza 2 de 2)

14 Programación con VisualAge RPG

Page 33: c 0924494

Creación de mensajesPara añadir mensajes, seleccione Proyecto→Definir mensajes en el Diseñador GUI.Aparecerá la ventana Definir mensajes. Seleccione Create, y luego seleccione el tipode mensaje que desea crear (por ejemplo, información o aviso). Escriba el texto delmensaje y cualquier información adicional o ayuda de segundo nivel en losespacios que se proporcionan.

VisualAge RPG genera automáticamente un ID de mensaje para el mensaje quecrea. Haga referencia a ese ID de mensaje en el código. Por ejemplo, en la Figura 3en la página 10, el código de operación DSPLY utiliza MSG0001.

Creación de la ayuda en líneaHemos añadido distintos tipos de ayuda a la aplicación Catálogo de vídeos. Lassiguientes secciones describen cómo puede reproducirse parte de esta ayuda.

Ayuda según contextoAñada ayuda según el contexto al componente pulsador gráfico Búsqueda porcategoría seleccionando Help text del menú emergente del componente. Esto iniciauna sesión de edición que ya contiene información similar a la que se muestra enla Figura 7.

:h1 res=01. es un código de cabecera que contiene un identificador de recurso. Elidentificador de recurso se genera automáticamente — no edite este texto. Lacabecera aparece justo después de este código; se utiliza en el panel de ayuda y selista en el índice de ayuda en tiempo de ejecución. Por omisión, el nombre delcomponente para el que se añade texto se utiliza como cabecera. Debe sustituirlopor una cabecera que identifique el propósito del panel de ayuda y que sea mássignificativa para los usuarios. Escriba el texto de ayuda después del código :p·.Por omisión aparece la palabra Ayuda en la sesión de edición.

En la Figura 8 se muestra un ejemplo de texto de ayuda de la aplicación Catálogode vídeos. El panel de ayuda que se genera a partir de ese código fuente y sevisualiza en tiempo de ejecución se muestra en la Figura 9 en la página 16.

:h1 res=01.PSB0000C:p.Ayuda

Figura 7. Sesión de edición para añadir ayuda en línea

:h1 res=12.Browse by Category:p.Seleccione esto para buscar vídeos por categorías.

Figura 8. Ayuda para el pulsador gráfico Búsqueda por categoría

Capítulo 1. Creación de una aplicación Cliente/Servidor 15

Page 34: c 0924494

Creación de pulsadores de ayudaPara crear el pulsador gráfico de ayuda en la parte inferior de la ventana Previewo de la ventana Comedy, seleccione un pulsador gráfico desde la paleta decomponentes con el botón derecho del ratón, mueva el puntero sobre la ventana dediseño y vuelva a pulsar con el botón derecho. En el cuaderno de propiedades,especifique la imagen que va a visualizarse en el pulsador gráfico y que deseavisualizar ayuda cuando se produzca el evento Press.

La Figura 10 muestra el fuente para el pulsador que proporciona ayuda para laventana Welcome. El código :link· se utiliza para enlazar fragmentos deinformación de ayuda relacionados de manera que los usuarios puedan encontrarla información adecuada de manera rápida y fácil. Coloque este código al principioy al final del texto relacionado con el texto de ayuda de otro panel. El texto queestá entre :link. y :elink. se resalta en la aplicación en tiempo de ejecución (veala Figura 11 en la página 17). Al seleccionar el texto resaltado, el usuario salta alpanel de ayuda destino relacionado. El id del recurso (resid) del panel destino esun parámetro del código de enlace.

Figura 9. Ejemplo de panel de ayuda en línea según el contexto

:h1 res=22.Get Help on using the Catalog:p.Select one of the graphic push buttons.:p.:link reftype=hd res=12.Browse by Category:elink.Press this button to browse by categories.:p.:link reftype=hd res=19.New Releases:elink.Press this button to view the new video releases.:p.:link reftype=hd res=20.Top 10 Bestsellers:elink.Press this button to view the 10 best ranked.:p.:link reftype=hd res=21.Search for Specific Titles:elink.Press this button to search for specific titles.

Figura 10. Ayuda para la ventana Welcome

16 Programación con VisualAge RPG

Page 35: c 0924494

Si desea obtener más información acerca de la creación de ayuda en línea para laaplicación, puede consultar los siguientes temas:v “Capítulo 13. Consejos para crear ayuda en línea con IPF” en la página 235v “Capítulo 14. Consejos para la creación y utilización de ayuda Windows” en la

página 239v “Capítulo 15. Consejos para la creación de JavaHelp” en la página 243

Repaso de la programación visualLos pasos descritos en las secciones anteriores son similares a los que se realizaránal crear una aplicación propia mediante VisualAge RPG. Estos pasos son:1. Decisión sobre lo que se mostrará al usuario

Antes de empezar a crear una aplicación nueva, debe decidir cuál es lafinalidad de la aplicación, cómo se presentará al usuario y cómo se comunicarácon otras aplicaciones.

2. Creación de la GUI utilizando el Diseñador GUIDespués de haber diseñado la aplicación, puede utilizar el Diseñador GUI paracrear la interfaz gráfica de usuario. VisualAge RPG proporciona un catálogo decomponentes de GUI entre los que elegir, y le proporciona la capacidad decrear componentes definidos por el usuario para ajustarse a sus necesidades.Puede seleccionar los componentes que desea que ver en la interfaz yseleccionar sus posiciones en una ventana de diseño. Personalice loscomponentes como sea necesario.Consulte el manual Iniciación a VisualAge RPG y CODE/400 y la ayuda en líneapara obtener información acerca de cómo crear ventanas, añadir componentes ala ventana, alinearlas y personalizarlas.

3. Obtención y establecimiento de atributosPuede establecer algunos atributos de componente durante el diseño medianteel cuaderno de propiedades del componente. También puede utilizar loscódigos de operación GETATR y SETATR, o las funciones incorporadas %getatry %setatr, para cambiar o recuperar los atributos para algunos componentes entiempo de ejecución. Al obtener o establecer atributos de componente, puedehacer referencia a un componente utilizando el nombre definido a este efectoen el Diseñador GUI.Para obtener más información acerca de los componentes y de cómo puedeobtenerlos y establecerlos, consulte el manual VisualAge RPG Manual de consultade componentes.

4. Escritura de la lógica de programa

Figura 11. Ejemplo de ayuda para una ventana que contiene un enlace de hipertexto

Capítulo 1. Creación de una aplicación Cliente/Servidor 17

Page 36: c 0924494

Cada componente responde a un conjunto de eventos predefinidos.Habitualmente, los eventos se generan como resultado de una interacción delusuario con la GUI. Por ejemplo, seleccionar un pulsador señala un eventoPress. El programa también puede generar eventos. Por ejemplo, el componentecliente DDE genera un evento Timeout si no puede iniciar una conversacióncon un programa servidor dentro de un período de tiempo predeterminado.Responda a eventos en el programa codificando los códigos de operaciónBEGACT (iniciar acción) y ENDACT (finalizar acción). El código entre estoscódigos de operación, denominado subrutina de acción, se ejecuta para unevento en particular. Si no codifica una subrutina de acción, no se emprendeninguna acción cuando se produce el evento.

5. Adición de mensajes y ayuda en líneaAdemás de crear la GUI y escribir parte de la lógica de programa para que seejecute, puede añadir mensajes y ayuda en línea a la aplicación.

18 Programación con VisualAge RPG

Page 37: c 0924494

Capítulo 2. Planificación de la aplicación

En esta sección se analiza el trabajo que debe realizar antes de empezar a codificaruna nueva aplicación o convertir una aplicación OS/400* existente en unaaplicación VisualAge RPG.

Si está creando una aplicación nueva, éste es el momento en que tiene que decidirsobre el propósito de su aplicación, cómo se presentará al usuario y cómo secomunicará con otras aplicaciones.

Si piensa reutilizar una aplicación OS/400 existente, éste es el momento de evaluarlas antiguas pantallas de caracteres y decidir cómo mejorarlas mediante la potenciade los componentes de interfaz gráfica de usuario. (Para obtener más informaciónacerca de reutilizar las aplicaciones existentes, vea “Parte 3. Cómo trabajar condatos AS/400” en la página 187.)

La información de esta sección le ayudará a diseñar una aplicación que satisfagalas necesidades del usuario y sea práctica para implantar.

Habilitación de aplicaciones seguras de JavaSi tiene intención de desplegar aplicaciones Java para su uso en la World WideWeb, tenga en cuenta que únicamente los sistemas AS/400 que se ejecuten enOS/400, Versión 4 Release 4, o posterior, dan soporte a la especificación Capa deSockets Segura (SSL). El flujo de datos entre las aplicaciones de estación de trabajoy los servidores AS/400 que ejecutan versiones anteriores de OS/400 no seráseguro.

Si desea obtener información sobre la configuración del soporte de SSL paraVisualAge RPG, puede consultar el manual Instalación de VisualAge RPG yCODE/400 para AS/400. Si las aplicaciones VARPG van a ejecutar applets queutilicen el archivo de seguridad cliente, consulte la publicación “Utilización delarchivo de seguridad para los applets” en la página 198.

Decidir qué funciones se van a proporcionarEn primer lugar, determine cuál es el propósito principal de la aplicación y quéfunciones debe proporcionar para llevarlo a cabo. Después de determinar lasfunciones esenciales, aborde las funciones avanzadas, tales como el intercambiodinámico de datos (DDE) y la impresión.

Ayuda a los usuariosLos usuarios tendrán grados diversos de experiencia con las GUI. Piense enproporcionar ayuda en línea adecuada para el nivel de conocimientos de unusuario típico. VisualAge RPG le facilita añadir ayuda en línea a la GUI. Se puedenañadir cuatro tipos de ayuda:

Ayuda según contextoInformación de ayuda que se adapta al contexto actual de una opción, unobjeto o un grupo de opciones u objetos.

© Copyright IBM Corp. 1994, 2000 19

Page 38: c 0924494

Ayuda para tareasInformación acerca de tareas que el usuario puede realizar con laaplicación.

Ayuda para herramientasGlobos de ayuda acerca de las herramientas disponibles para el usuario.

Ayuda a nivel de ventanaInformación acerca del contenido de una ventana.

También se puede ayudar a los usuarios proporcionándoles toda la informaciónque necesitan para completar una tarea y suministrar solicitudes y etiquetas consignificado en los componentes de GUI. Puede utilizar puntos suspensivos (...) paraindicar que se necesita más información antes de poder realizar una accióndeterminada. (Por ejemplo, utilice Visualizar... para que los usuarios sepan que seles solicitará más información antes de que se lleve a cabo la acción de visualizar).No utilice puntos suspensivos en una etiqueta si la acción se realizaráinmediatamente después de pulsar el botón. Por ejemplo, el botón Ayuda nonecesita puntos suspensivos en la etiqueta, porque la información de ayuda sevisualiza en cuanto se pulsa el botón. También puede proporcionar ayuda en formade un campo de texto estático que se actualiza cuando el puntero del ratón semueve sobre diferentes componentes de la interfaz.

Puede minimizar la cantidad de información que los usuarios tienen queproporcionar estableciendo valores por omisión. Por ejemplo, puede utilizar unrecuadro de combinación para dar a los usuarios la opción de seleccionarelementos en una lista de opciones utilizadas habitualmente. Esto evita errores detecleo durante la ejecución.

Mantener un diseño de ventana sencilloHay dos aspectos básicos en un buen diseño de ventana:v El número y la estructura de las ventanas en la aplicaciónv El contenido de cada ventana

Número de ventanasEs aconsejable tener una ventana principal desde la que el usuario pueda iniciartodas las tareas principales. Proporcione ventanas secundarias para obtenerinformación adicional que los usuarios deben especificar para completar una tarea.

Evite que haya muchas ventanas anidadas, porque demasiadas capas hacen queuna tarea sencilla parezca compleja. Recuerde también que demasiadas ventanasllenarán toda la pantalla del usuario, especialmente si éste está ejecutando más deuna aplicación. Los usuarios también pueden desorientarse si tienen muchasventanas en la pantalla.

Intente minimizar el número de componentes de cada ventana. Esto aumentará elrendimiento cuando se visualicen ventanas. Una aplicación con muchas ventanas ypocos componentes por ventana funcionará mejor que la misma aplicación conpocas ventanas y muchos componentes por ventana.

Contenido de cada ventanaAgrupe toda la información relacionada en un solo lugar. Utilice el componenterecuadro de grupo y el componente recuadro de contorno para indicar visualmentequé botones de selección están relacionados.

20 Programación con VisualAge RPG

Page 39: c 0924494

Utilice imágenes gráficas e iconos para identificar tareas o para complementar laspalabras de la ventana. Asegúrese de que todo el texto está escrito correctamente.

Sitúe los componentes en las ventanas de una manera ordenada y lógica. No espreciso que planifique la posición de algunos componentes, porque su posiciónestá predeterminada. Por ejemplo, un componente barra de menús siempre seubica justo debajo de la barra de título de una ventana.

Si las ventanas tienen componentes comunes, debe visualizar esos componentes enuna ubicación coherente. Esto facilita a los usuarios encontrar información común.

Planificar el código con eficaciaDespués de diseñar la GUI, debe decidir qué código se necesita para soportar lasacciones que realizarán los usuarios de la aplicación. VisualAge RPG le ayuda acrear la GUI sin escribir mucho código; realiza las tareas rutinarias en su lugar.Todos los componentes tienen atributos por omisión, que pueden modificarsemediante el Diseñador GUI o en el programa. Tiene que establecer explícitamenteotros atributos. Por ejemplo, si desea que los usuarios puedan ver gráficosaccionando un pulsador con la etiqueta Visualizar..., debe hacer algo más queseñalar y pulsar el componente pulsador de la paleta en la ventana de diseño: porlo menos debe establecer el atributo de etiqueta para que ponga Visualizar... yescribir la lógica para buscar y visualizar los datos.

Mantener informados a los usuariosUtilice mensajes para proporcionar información particularmente importante ourgente al usuario. Dé mensajes detallados, pero no excesivamente complicados,que describan el problema y, si es posible, que expliquen cómo corregirlo.VisualAge RPG proporciona tres maneras de visualizar mensajes y debe elegirse elmétodo más apropiado para el tipo de información que se desee visualizar:

VentanaPara proporcionar información urgente que el usuario debe conocer; porejemplo, un proceso que no se ha completado de manera satisfactoria.

Subarchivo de mensajesPara proporcionar información acerca de una opción, o para contener unmensaje acerca de la realización de una acción o un proceso.

Ayuda de mensaje de segundo nivelPara proporcionar un nivel extra de detalle que puede no ser necesario entodas las ocasiones para todos los usuarios; por ejemplo, describir un cursode acción que los usuarios novatos tal vez no conozcan.

Puede que desee añadir un indicador de progreso para los procesos más largos,con el fin de mantener informado al usuario.

Planifique proporcionar indicaciones de texto, visuales o auditivas a los usuariospara presentar excepciones. Por ejemplo, puede mostrar a un usuario que unpulsador no está disponible atenuando el texto en el botón. No se puedenplanificar todas las posibles acciones de los usuarios, por lo que debe planificartambién cómo informará la aplicación a los usuarios de que hay acciones que nopuede interpretar. Por ejemplo, puede visualizar un mensaje en una ventana si unusuario intenta salir de un archivo sin guardar los cambios efectuados durante unasesión de edición.

Capítulo 2. Planificación de la aplicación 21

Page 40: c 0924494

Utilizar un estilo coherenteUtilice términos coherentes para minimizar las confusiones. Por ejemplo, si utilizaInicio de sesión en una ventana, no utilice ID de usuario para referirse al mismoconcepto en otro lugar.

Utilice nemotécnicos coherentes en todas las ventanas de la aplicación. Unnemotécnico es una tecla de letra que puede pulsarse para seleccionar una eleccióno realizar una acción. La tecla de letra corresponde a la letra subrayada de unaopción en un pulsador o en un menú. Por ejemplo, si utiliza Guardar pararepresentar la función de guardar en un pulsador de una ventana, utilícelo entodas las ventanas que tengan ese pulsador.

Anticipar cuestiones de traducciónAunque sus planes actuales no incluyan la traducción de la aplicación a otroidioma, debe diseñar y crear la aplicación de tal manera que pueda traducirse confacilidad en el futuro. Si lo hace, tendrá menos trabajo de reacondicionamientocuando surja la necesidad de traducirla.

No olvide mantener el código ejecutable separado del texto. De esta manera puedeutilizar el texto en el idioma adecuado sin el código ejecutable estándar.

Nota: Hay otras razones por las que debe pensar en separar el texto del código.Puede corregir errores en el texto y efectuar cambios en la terminología conmayor facilidad en releases futuros.

Puede crear archivos de mensajes separados para cada idioma y asignar distintasextensiones de archivo a cada uno de ellos. Cada uno de los archivos de mensajesdeben tener números de mensaje idénticos, pero el texto estará escrito en unidioma distinto. Puede construir un archivo ·EXE para todos los idiomas utilizandoel archivo de mensajes adecuado. Por ejemplo, la versión inglesa del archivo demensajes compilado podría denominarse SAMPLE·ENG; y la versión alemana,SAMPLE·GER. Puede indicar a los usuarios que redenominen el archivo demensajes correspondiente a SAMPLE·MSG antes de ejecutar la aplicación. Paraobtener más información, vea el “Capítulo 16. Trabajar con mensajes” en lapágina 247.

Tenga también en cuenta que la traducción puede cambiar los requisitos de tamañodel texto (como las etiquetas), los campos de entrada, el almacenamientointermedio y las ventanas. Al definir el tamaño de un componente en el DiseñadorGUI que tendrá una etiqueta de sustitución, tenga en cuenta que el texto traducidopuede ser más largo que el original.

Si utiliza nemotécnicos, recuerde que el carácter nemotécnico puede ser diferentepara distintos idiomas.

22 Programación con VisualAge RPG

Page 41: c 0924494

Parte 2. Cómo trabajar con componentes“Capítulo 3. Programación con componentes” en la página 25

Proporciona una visión general de las tareas de programación generalesque debe realizar para controlar los componentes GUI.

“Capítulo 4. Programas de ejemplo para VisualAge RPG” en la página 33Describe cómo utilizar programas de ejemplo para algunos componentesVisualAge RPG.

“Capítulo 5. Atributos comunes” en la página 35Describe atributos que son comunes a la mayoría de los componentes ycómo puede utilizarlos.

“Capítulo 6. Utilización de transferencia de datos” en la página 41Describe cómo puede utilizar la transferencia de datos para manipular elvalor de algunos componentes.

“Capítulo 7. Utilización de componentes” en la página 45Contiene sugerencias útiles acerca de la utilización de componentesVisualAge RPG.

© Copyright IBM Corp. 1994, 2000 23

Page 42: c 0924494

24 Programación con VisualAge RPG

Page 43: c 0924494

Capítulo 3. Programación con componentes

En esta sección se describen algunos consejos para programar con componentes.Los temas tratados incluyen cómo obtener y establecer atributos de componente,hacer referencia a componentes del programa, responder a eventos y atributos delsistema, trabajar con atributos de evento y del sistema, y codificar componentes detexto estático y de campo de entrada.

Obtención y establecimiento de atributos de componentePuede establecer algunos atributos de componente durante el tiempo de diseñomediante el cuaderno de propiedades del componente. También puede utilizar loscódigos de operación GETATR y SETATR, o las funciones incorporadas %getatr y%setatr, para cambiar o recuperar los atributos para algunos componentes entiempo de ejecución. Para obtener más información acerca de los atributos y dóndepuede establecerlos, consulte el manual VisualAge RPG Manual de consulta decomponentes.

GETATR y SETATR son códigos de operación fijos que pueden utilizarse parahacer referencia a componentes en la misma ventana como el componente que hagenerado el evento. Por ejemplo, si el componente que ha generado el evento estáen WINDOW1, los códigos de operación fijos sólo pueden hacer referencia acomponentes en WINDOW1. Si un código de operación GETATR o SETATR hacereferencia a un componente en otra ventana, se producen errores de tiempo decompilación para las subrutinas de acción de enlace único, porque el compiladorverifica que el componente referenciado exista en esa ventana. Se producen erroresen tiempo de ejecución para las subrutinas de acción de múltiples enlaces.

Para hacer referencia a componentes en distintas ventanas, debe utilizar lasfunciones incorporadas %getatr y %setatr. Puede utilizar estas funcionesincorporadas para especificar el nombre de ventana y el nombre de componente.

Consulte el manual VisualAge RPG Manual de consulta del lenguaje, para obtenerinformación acerca de la utilización de estos códigos de operación y funcionesincorporadas.

Referencia a componentes en el programaAl obtener o establecer atributos de componente, puede hacer referencia a uncomponente utilizando el nombre definido a este efecto en el Diseñador GUI. Elnombre debe seguir los convenios de denominación del sistema AS/400.Específicamente, el nombre:v No debe exceder de 10 caracteres de longitud. Sólo se permiten caracteres SBCS.

Los caracteres deben ser letras de la A a la Z, números del 0 al 9 o los símbolos@, #, $ o _ (subrayado).

v Debe empezar por las letras de la A a la Z, o por los símbolos @, #, o $.v Puede entrarse en mayúsculas o en minúsculas.v No debe contener blancos intercalados.v No debe ser un nombre ampliado (es decir, no debe estar encerrado entre

comillas).

Nota: Cuando está ejecutándose el programa, sólo puede hacer referencia acomponentes que se han creado. Los componentes se crean cuando también

© Copyright IBM Corp. 1994, 2000 25

Page 44: c 0924494

se crea la ventana donde están. Al crear una ventana o un componente, secarga en la memoria. Cualquier intento de hacer referencia a un componenteque todavía no se ha creado da como resultado un mensaje Componente noencontrado.

Respuesta a eventosCada componente responde a un conjunto de eventos predefinidos. Puede utilizaruno de los siguientes métodos para obtener una lista de eventos predefinidos:1. Consulte el manual VisualAge RPG Manual de consulta de componentes si desea

ver una lista completa.2. Pulse F1 cuando el foco esté en el componente de la paleta o del catálogo para

obtener una descripción general del componente y una lista de los atributos yeventos asociados con ese componente.

3. En el Diseñador GUI, invoque el menú emergente para el componente yseleccione el elemento Eventos.

Habitualmente, los eventos se generan como resultado de alguna interacción con lainterfaz de usuario. Por ejemplo, al accionar un pulsador se señala un eventoPress. El programa también puede generar eventos. Por ejemplo, el componentecliente DDE genera un evento Timeout si no puede iniciar una conversación conun programa servidor dentro de un período de tiempo predeterminado. Si elprograma cambia el valor del texto de un componente campo de entrada, el campode entrada señala un evento Change.

Responda a eventos en el programa codificando los códigos de operación BEGACT(iniciar acción) y ENDACT (finalizar acción). El código entre estos códigos deoperación, denominado subrutina de acción, se ejecuta para un evento enparticular. Cuando se crea una subrutina de acción para un evento específico, sedefine un enlace de acción. Si no codifica una subrutina de acción para un eventoen particular, no se emprende ninguna acción cuando se produce el evento. Elcódigo en una subrutina de acción se ejecuta hasta que se alcanza el código deoperación ENDACT. Por consiguiente, si ha codificado códigos de operación EXSRdentro de una subrutina de acción, estas subrutinas (denominadas subrutinas deusuario) también se ejecutan.

No puede invocar una subrutina de acción utilizando el código de operaciónEXSR. Sin embargo, puede invocar una subrutina de acción en particular mediantemás de una acción. Por ejemplo, puede tener un código que se ejecuta cuando seacciona un pulsador o cuando se selecciona un elemento de menú. Puede revisarlos eventos que tienen subrutinas de acción y modificar eventos de enlace asubrutinas de acción en la ventana Subrutinas de acción. Para visualizar la ventanaSubrutinas de acción:1. Seleccione Editar código fuente del menú Proyecto en el Diseñador GUI. Esto

inicia una sesión de edición.2. Desde la sesión de edición, seleccione Editar→Subrutinas de acción. Aparece la

ventana Subrutinas de acción.

Los atributos de evento contienen datos que son relevantes para un evento. Porejemplo, el evento MouseMove almacena las coordenadas X e Y para indicardónde estaba ubicado el ratón cuando se produjo el evento. Antes de que puedautilizar atributos de evento en el programa, deben definirse en especificaciones dedefinición. El nombre del atributo de evento es el nombre de la entidad en laespecificación de definición. Dado que el compilador no verifica la longitud de lavariable y algunos atributos tienen longitudes variables, asegúrese de especificaruna longitud lo bastante grande para contener el valor esperado.

26 Programación con VisualAge RPG

Page 45: c 0924494

Nota: El programa no puede cambiar los atributos de evento. Por consiguiente, nopueden aparecer en un campo de resultado como el campo destino para unaoperación EVAL.

En el manual VisualAge RPG Manual de consulta de componentes se describen todoslos atributos de evento.

El siguiente ejemplo muestra cómo los atributos de evento %MouseX y %MouseYpueden definirse y utilizarse en un programa.

Atributos de sistemaLos atributos de sistema pertenecen a la aplicación y no a un componenteespecífico.

Como sucede con los atributos de evento, los atributos de sistema deben definirseen una especificación de definición. El programa no puede modificar los atributosde sistema.

VisualAge RPG soporta los siguientes atributos de sistema:

Tabla 1. Atributos de sistema

Atributo Descripción Tipo Longitud

%DspHeight Devuelve la altura dela pantalla, en tiempode ejecución, enpixels.

Numérico 4

%DspWidth Devuelve la anchurade la pantalla, entiempo de ejecución,en pixels.

Numérico 4

Cómo trabajar con atributos de evento y de sistemaCada atributo de evento es válido para un evento en particular y sólo puedeutilizarse en subrutinas de acción que están enlazadas con dicho evento. Porejemplo, si utiliza un atributo de evento para el evento MouseMove dentro de unasubrutina de acción que está enlazada con el evento ReSize, se emite un error detiempo de ejecución. La comprobación de tipos en los atributos de evento sólo se

** Definir atributos de evento de coordenadas x e y del ratón*

DName+++++++++++ETDsFrom+++To/L+++IDc.Keywords++++++++++++++++++++++++D%MouseX S 4P 0D%MouseY S 4P 0** Comprobar si las coordenadas del ratón están en el rango:*

CSRN01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEq...CSRN01Factor1+++++++Opcode(E)+Extended-factor2++++++++++++++++++++++++++C %MouseX ifgt 100C %MouseY andgt 100C ..C endif****** Fin de fuente

Capítulo 3. Programación con componentes 27

Page 46: c 0924494

realiza en tiempo de ejecución. Si define un campo de tipo carácter para unatributo de evento numérico, este error sólo se detecta en tiempo de ejecución.

Los atributos del sistema pueden utilizarse en cualquier lugar del programa,porque no están enlazados con ningún evento en particular. La comprobación detipos en los atributos de evento se realiza en tiempo de compilación.

Los atributos de evento y de sistema deben definirse en una especificación dedefinición antes de que puedan utilizarse en todo el componente lógico VisualAgeRPG. El compilador los trata como campos de sólo lectura en el almacenamientoautomático. Cualquier subrutina de acción anidada y activa tiene su propia copiade un atributo de evento.

Por ejemplo, suponga que la subrutina de acción ENT0000A+CHANGE+WIN1 estáenlazada a la ventana WIN1, al componente campo de entrada ENT0000A y alevento CHANGE.

Suponga también que la subrutina PSB0000A+PRESS+WIN1 está enlazada a laventana WIN1, al componente pulsador PSB0000A y al evento PRESS.

Cuando se acciona el pulsador PSB0000A, se invoca la subrutina de acciónPSB0000A+PRESS+WIN1. Cuando se ejecuta la operación SETATR, se desencadenael evento CHANGE para el componente campo de entrada ENT0000A. Esto invocala subrutina de acción ENT0000A+CHANGE+WIN1.

Cada subrutina de acción tiene su propio almacenamiento para %PART porque loscampos de atributo de evento están en el almacenamiento automático:v En la subrutina de acción PSB0000A+PRESS+WIN1, %PART contiene

’PSB0000A’.v En la subrutina de acción ENT0000A+CHANGE+WIN1, %PART contiene

’ENT0000A’.

CSRN01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEq..CSRN01Factor1+++++++Opcode(E)+Extended-factor2+++++++++++++++++++++++C ENT0000A BEGACT CHANGE WIN1C .C .C %PART dsply boxid reply* Se visualiza 'ENT0000A'.

C .C .C endact

CSRN01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEq..CSRN01Factor1+++++++Opcode(E)+Extended-factor2++++++++++++++++++++++++C PSB0000A BEGACT PRESS WIN1C .C %PART dsply boxid reply* Se visualiza 'PSB0000A'.

C .C ENT0000A SETATR 10 TEXT* Desencadena el evento CHANGE para el campo de entrada ENT0000A* que hace que se invoque la subrutina de acción ENT0000A+CHANGE+WIN1.*

C .C .C %PART dsply boxid reply* Se visualiza 'PSB0000A'.

C .C .C endact

28 Programación con VisualAge RPG

Page 47: c 0924494

v Cuando se completa la subrutina de acción ENT0000A+CHANGE+WIN1 y lasubrutina de acción PSB0000A+PRESS+WIN1 sigue ejecutándose, %PARTcontiene ’PSB0000A’, no ’ENT0000A’.

Codificación de los componentes texto estático y campo de entradaLa siguiente sección contiene algunos consejos para codificar componentes textoestático y campo de entrada.

Creación y recuperación de componentes campo de entrada

Nota: Esta sección también se aplica a componentes texto estático. Para simplificar,en el texto sólo se mencionan los componentes campo de entrada.

Cuando se ejecuta una operación READ, ¿dónde almacena VisualAge RPG el valorrecuperado? Cuando se ejecuta una operación WRITE, ¿qué valor utiliza VisualAgeRPG para establecer el valor?

Para cada componente campo de entrada, VisualAge RPG crea un campo con elmismo nombre que el componente. Este campo se define para que coincida con ladefinición del atributo Text (o el atributo Label para los componentes textoestático). Por ejemplo, si hay un componente campo de entrada denominadoENT00012, y el atributo Text está definido como de 20 caracteres, VRPG defineautomáticamente un campo de 20 caracteres denominado ENT00012. Puede utilizareste campo en el programa.

Puede alterar temporalmente la definición del campo en una especificación dedefinición, definiendo un campo del mismo nombre. No obstante, la definición delcampo debe cumplir las reglas de VisualAge RPG respecto a la compatibilidad detipo y longitud. Por ejemplo, el campo debe tener la misma longitud que ladefinición de atributo. Para los campos numéricos, el campo no ha de tener elmismo tipo que la definición de atributo.

Cuando se ejecuta la aplicación, el valor de un campo de entrada se inicializa conel valor suministrado en el Diseñador GUI. No obstante, puede sobreescribir estevalor estableciendo la palabra clave INZ en la especificación de definición omoviendo un valor al campo de programa. En estos casos, el valor almacenado encada uno de estos campos no coincide necesariamente con el valor que verá en lapantalla para el componente correspondiente.

Si almacena un valor diferente en un campo en una subrutina de usuario o deacción, VisualAge RPG no refleja ese nuevo valor en la pantalla. Por consiguiente,el valor almacenado en el campo es diferente del visualizado en la pantalla. Parareflejar el valor almacenado en la pantalla, debe utilizar una operación WRITE ouna operación SETATR.

Lo mismo es válido para SHOWWIN. Cuando una ventana se abre por primeravez, los valores que aparecen en la pantalla corresponden a los valoressuministrados para los componentes del Diseñador GUI. Si cambia el valoralmacenado para un campo VisualAge RPG correspondiente antes de mostrar laventana, el valor del campo no coincidirá con lo que se ve en la pantalla. Para quelos dos valores sean idénticos, tiene que realizar una operación WRITE o unaoperación de establecer atributos en una subrutina de acción enlazada al eventoCreate para la ventana. Esto sincroniza el valor almacenado en el campo con elvalor de la pantalla y el usuario sólo ve el nuevo valor cuando se muestra laventana.

Capítulo 3. Programación con componentes 29

Page 48: c 0924494

En general, es aconsejable utilizar una subrutina de acción enlazada al eventoCreate para establecer valores que deben aparecer en la pantalla cuando se abreuna ventana.

Códigos de operación para componentes de ventanaSe han ampliado varios códigos de operación en VisualAge RPG para quefuncionen en ventanas y sus componentes: READ, WRITE, CLEAR y RESET. Estoscódigos de operación pueden utilizarse en ventanas y afectan a los componentestexto estático y campo de entrada.

READ Ejecuta operaciones de obtener atributos en todos los componentes textoestático y campo de entrada afectados.

WRITEEjecuta operaciones de establecer atributos en todos los componentes textoestático y campo de entrada afectados.

CLEAREstablece todos los componentes campo de entrada numérico en cero ytodos los componentes campo de entrada de tipo carácter en blancos. (Nofunciona en los componentes texto estático.)

RESETEstablece de nuevo los componentes texto estático y campo de entrada ensus valores iniciales.

Los códigos de operación de ventana utilizan estos atributos:

Text Atributo de los componentes campo de entrada que se utiliza para ejecutaroperaciones READ, WRITE, CLEAR y RESET.

Label Atributo de componentes texto estático que se utiliza para ejecutaroperaciones READ, WRITE y RESET.

Utilización de códigos de operación de ventana encomponentes con nombres idénticos

Puede tener dos campos de entrada con el mismo nombre, dos componentes textoestático con el mismo nombre, o incluso un componente campo de entrada quetenga el mismo nombre que un componente texto estático, siempre y cuando loscomponentes pertenezcan a ventanas diferentes. Esta sección describe cómo evitarestablecer el valor de uno de estos componentes como valor de otro de manerainadvertida.

Sólo se crea un campo de programa para un nombre de componente determinado.Si hay un componente campo de entrada en la ventana W1 denominado MYPART,y un componente campo de entrada en la ventana W2 denominado MYPART, secrea un campo VisualAge RPG denominado MYPART. El compilador crea ladefinición de manera que coincida con una de las definiciones de componente.

Si tiene más de un componente con el mismo nombre, el compilador emitirá unmensaje de error si los componentes no tienen definiciones compatibles. Loscomponentes son compatibles si aceptan el mismo tipo de datos (numérico o detipo carácter), tienen la misma longitud y (si son numéricos) tienen el mismonúmero de posiciones decimales.

Si los componentes que comparten un campo tienen valores iniciales diferentes, elvalor inicial del campo se establece según el componente que el compiladorencuentre primero al crear los campos internos para componentes campo de

30 Programación con VisualAge RPG

Page 49: c 0924494

entrada. Esto puede variar de una construcción a otra, de manera que cuandovarios componentes comparten el mismo campo, no debe dependerse del campoque tenga un valor inicial específico, a menos que se establezcan todos los valoresiniciales como iguales.

Ejecutar una operación en una de las ventanas que contiene uno de estoscomponentes, o en uno de los componentes, da como resultado que el campo deentrada contenga un valor que coincida con el valor de pantalla del componenteimplicado en la operación. No obstante, el campo contiene un valor queprobablemente no coincide con los valores de pantalla de los otros componentes enotras ventanas que comparten este campo. Aunque varios componentes compartenel mismo campo, una operación en cualquiera de estos componentes sólo afecta alcomponente especificado en la operación o contenido en la ventana especificada enla operación. Los otros componentes que comparten el campo no se ven afectados.

EjemploEl siguiente ejemplo muestra lo que puede suceder cuando se establece el valor deuno de los componentes en un valor de otro componente cuando éstos compartenun campo.

1· Definición de los campos: El campo de entrada A01 en la ventana W1 sedefine como de 10 caracteres, al igual que en la ventana W2. El valor en la pantallapara W1 es 78893, y el valor en la pantalla para W2 es 885364. El campo A01contiene el valor 0000000000. Estos son los valores iniciales.

2· Ejecución de una operación READ en W1: El campo A01 contiene ahora 78893.Coincide con el campo de entrada A01 en W1.

3· Ejecución de una operación WRITE en W2: El valor de pantalla del campo deentrada A01 en W2 es ahora 78893.

4· Ejecución de una operación CLEAR en W2: El campo A01 contiene ahorablancos. Coincide con el campo de entrada A01 en W2. Campo de entrada A01 enW1 - el valor en pantalla es 78893. Campo de entrada A01 en W2 - el valor enpantalla es un blanco.

W 1 W 2 Program Field

A01 78893 885364 0000000000A01 A01

W 1 W 2 Program Field

A01 78893 885364 78893A01 A01

W 1 W 2 Program Field

A01 78893 78893 78893A01 A01

Capítulo 3. Programación con componentes 31

Page 50: c 0924494

5· Ejecución de una operación GETATR en el campo de entrada A01 de W1 conel campo destino A01: El campo A01 contiene ahora 78893. Coincide con elcampo de entrada A01 en W1.

Si desea que todos los componentes que comparten un campo visualicen el mismovalor, tiene que ejecutar operaciones SETATR en todos los componentes utilizandoel campo como valor fuente, o ejecutar operaciones WRITE en todas las ventanasque contengan uno de estos componentes.

Es recomendable dar nombres exclusivos a todos los componentes campo deentrada en el componente lógico, para impedir que se establezca accidentalmenteel valor de uno de los componentes como el valor de otro.

W 1 W 2 Program Field

A01 78893 A01 A01

W 1 W 2 Program Field

A01 78893 78893A01 A01

32 Programación con VisualAge RPG

Page 51: c 0924494

Capítulo 4. Programas de ejemplo para VisualAge RPG

La carpeta Ejemplos (de la carpeta de proyectos de VisualAge RPG) contiene elcódigo fuente y la versión de tiempo de ejecución de las aplicaciones de ejemploanalizadas en esta parte del manual. La Tabla 2 lista los programas de ejemplo.

Tabla 2. Programas de ejemplo para VisualAge RPG

Programa Descripción

Animation Ejemplo de componente control deanimación

Bean Ejemplo de componente bean Java

Calendar Ejemplo de componente calendario

Component Reference Part Ejemplo de referencia del componente

Container Ejemplo del componente contenedor

Customer Maintenance* Ejemplo de mantenimiento de clientes

DDE Client Ejemplo de componente cliente DDE

DDE Hotlink Ejemplo de enlace dinámico DDE

Drag and Drop Ejemplo de transferencia de datos

Graph Ejemplo de componente gráfico

Image* Ejemplo de componente imagen

Listbox Ejemplo de componente recuadro de lista

Message Subfile Ejemplo de componente subarchivo demensajes

Multiline Edit Ejemplo de componente edición demúltiples líneas

Notebook Ejemplo del componente cuaderno

Odbcceld Ejemplo de componente interfazODBC/JDBC

Popup Menu Ejemplo del componente menú emergente

Progress Ejemplo de componente barra de progreso

Resize Ejemplo de ajuste de tamaño

Scroll Ejemplo de componente barra dedesplazamiento

Slider** Ejemplo de componente graduador

Spin Button Ejemplo de componente selector cíclico

Subfile* Ejemplo de componente subarchivo

Timer Ejemplo de componente temporizador

VARPG Plug-in Ejemplo de conector de proveedor

Video Store Cashier* Ejemplo de cajero de tienda de vídeos

Video Store Catalog* Ejemplo de catálogo de vídeos

Welcome Ejemplo de bienvenida

© Copyright IBM Corp. 1994, 2000 33

Page 52: c 0924494

Notas:

1. * Este ejemplo requiere datos en un sistema AS/400.2. ** También muestra cómo utilizar los atributos BackMix y ForeMix.

Antes de empezarAntes de ejecutar e instalar las aplicaciones de ejemplo, debe instalar VisualAgeRPG. Consulte el manual Instalación de VisualAge RPG y CODE/400 para AS/400,para obtener información y ejemplos de instalación.

Antes de utilizar los ejemplos, lea los comentarios del programa de ejemplo. Estoscomentarios contienen consejos y requisitos, así como posibles restricciones.

Para construir y ejecutar aplicaciones Java, debe tener instalado el Java 2 SoftwareDevelopment Kit (J2SDK) Versión 1.2, o superior, de Sun, en la estación de trabajo.Si no tiene el J2SDK, puede bajarlo de Sun Microsystems en el URL siguiente:http://www.javasoft.com/products/

Tras instalar el J2SDK, establezca la variable de entorno PATH de modo queapunte a la ubicación tanto del compilador Java como del Java RuntimeEnvironment (JRE). Por ejemplo, si el directorio inicial de J2SDK es c:\jdk1.2, añadala siguiente sentencia en la variable PATH: c:\jdk1.2\bin

Construcción de los ejemplosPuede ejecutar la mayoría de los ejemplos sin construirlos porque se proporcionauna versión de tiempo de ejecución.

Para construir uno de los programas de ejemplo, visualice el menú emergente de lacarpeta del ejemplo y seleccione Construir>Windows NT/95/98 o Construir>Java.

Ejecución de los ejemplosPara ejecutar un programa de ejemplo, visualice el menú emergente del programay seleccione Ejecutar>Windows NT/95/98 o Ejecutar>Java.

Acceso a un sistema AS/400Algunos programas de ejemplo, como el ejemplo de subarchivo, acceden a datosen un sistema AS/400. Los archivos de datos de AS/400 utilizados por estosprogramas no se envían con VisualAge RPG. No obstante, la sección de comentariode archivos fuente describe el diseño de archivo para ese ejemplo. Debe crear losarchivos de datos en el sistema AS/400 y suministrar datos.

Para ejecutar estos ejemplos, debe iniciar el Diseñador GUI en el programa ejemploy utilizar el cuaderno Definir información de AS/400 en el menú desplegableServidores para realizar lo siguiente:1. Cambie el parámetro de ubicación remota para que apunte al sistema AS/400

al que desee acceder.2. Cambie el parámetro de nombre de archivo remoto de tal manera que pueda

acceder al archivo de datos adecuado para el ejemplo.

Vea el “Capítulo 8. Conectividad con AS/400” en la página 189 para obtener másinformación sobre la definición de información de AS/400.

34 Programación con VisualAge RPG

Page 53: c 0924494

Capítulo 5. Atributos comunes

En esta sección se describen los atributos que son comunes a la mayoría de loscomponentes y cómo puede utilizarlos.

Atributo PartNameTodos los componentes tienen un nombre. VisualAge RPG genera automáticamenteeste nombre cuando se crea el componente. Puede cambiar el nombre delcomponente en su cuaderno de propiedades o editándolo directamente en la vistade árbol de la ventana de proyecto del Diseñador GUI. El nombre de componente*componente lógico no puede editarse.

Nota: No puede cambiar el nombre de componente en tiempo de ejecución.

Cada ventana debe tener un nombre exclusivo y todos los componentes en unaventana dada deben tener un nombre exclusivo. Los componentes de ventanasdiferentes pueden tener el mismo nombre, salvo los nombres de componentesubarchivo, que deben ser exclusivos en todo el componente lógico.

Implícitamente, el compilador define un nombre de campo para el campo deentrada y los componentes texto estático mediante el atributo PartName. Puedeutilizar ese nombre en el programa si desea referirse al valor de estoscomponentes. Para obtener más información, vea el “Capítulo 3. Programación concomponentes” en la página 25.

Si cambia el nombre de un componente, debe cambiar todas las referencias a esecomponente en el fuente del programa. Si intenta hacer referencia al nombreantiguo de un componente que se ha redenominado, obtendrá errores decompilación o un error de tiempo de ejecución indicando que no ha podidoencontrarse el componente.

Atributo ParentNameEl atributo ParentName devuelve el nombre del componente padre. El padre es laventana donde se coloca un componente. Para un componente ventana, el padre esla misma ventana.

Atributo PartTypePuede utilizar el atributo PartType para determinar el tipo de componente en elprograma. PartType devuelve el tipo del componente tal como lo define VisualAgeRPG. El valor devuelto para los componentes VisualAge RPG consiste en la serieFVDES seguida del tipo de componente. Por ejemplo, para un componente campode entrada el tipo de componente sería FVDESEntryField. Una excepción es elcomponente referencia a componente lógico, que tiene el prefijo FVDESV.

La Tabla 3 en la página 36 resume el valor del atributo PartType para cadacomponente VisualAge RPG.

© Copyright IBM Corp. 1994, 2000 35

Page 54: c 0924494

Tabla 3. El atributo PartType de VisualAge para componentes de RPG

Atributo PartType Componente VisualAge RPG

FVDESOCX ActiveX

FVDESAnimationControl Control de animación

FVDESCalendar Calendario

FVDESCanvas Lienzo

FVDESCheckBox Recuadro de selección

FVDESComboBox Recuadro de combinación

FVDESContainerControl Contenedor

FVDESVComponentReference Referencia a componente lógico

FVDESDDEClient Cliente DDE

FVDESEntryField Campo de entrada

FVDESGraph Gráfica

FVDESGraphicPushButton Pulsador gráfico

FVDESGroupBox Recuadro de grupo

FVDESHScrollBar Barra de desplazamiento horizontal

FVDESImage Imagen

FVDESJavaBean Bean Java

FVDESListBox Recuadro de lista

FVDESAudio Medios

FVDESMediaPanel Panel de medios

FVDESMenuItem Elemento de menú

FVDESMessageSubfile Subarchivo de mensajes

FVDESMultiLineEdit Edición de múltiples líneas

FVDESNotebook Cuaderno

FVDESNotebookPage Página de cuaderno

FVDESODBCInterface Interfaz ODBC/JDBC

FVDESOutlineBox Recuadro de contorno

FVDESPopUpMenu Menú emergente

FVDESProgressBar Barra de progreso

FVDESPushButton Pulsador

FVDESRadioButton Botón de selección

FVDESSlider Graduador

FVDESSpinButton Selector cíclico

FVDESStaticText Texto estático

FVDESStatusBar Barra de estado

FVDESSubfile Subarchivo

FVDESSubmenu Submenú

FVDESTimer Temporizador

FVDESVScrollBar Barra de desplazamiento vertical

FVDESFrameWindow Ventana

36 Programación con VisualAge RPG

Page 55: c 0924494

Atributos de colorPuede cambiar el color de la mayoría de componentes mediante los atributosBackColor y ForeColor. Los valores de atributo son números que representancolores específicos. El compilador proporciona un conjunto de constantesrepresentativas, tales como *RED y *GREEN, que pueden utilizarse para establecerlos colores. Puede dirigirse a la publicación VisualAge RPG Manual de consulta dellenguaje si desea consultar estos nombres.

Puede especificar una mezcla de colores para el componente mediante los atributosForeMix y BackMix. El valor de estos atributos representa una mezcla de loscolores primarios rojo, verde y azul. Suele hacerse referencia a esto como el valorde color RGB. Este valor RGB es una serie que se compone de tres valoresseparados por signos de dos puntos (:). Cada valor representa la intensidad derojo, verde y azul, por este orden. El valor de cada color está entre 0 y 255.

En el siguiente ejemplo de código, la mezcla de colores de fondo de uncomponente texto estático se establece en un tono medio de azul:

Para ver un ejemplo más detallado sobre cómo especificar los atributos ForeMix yBackMix, vea “Graduador” en la página 139.

Atributo EnabledCuando se habilita un componente, puede responder a la interacción del usuario ygenerar eventos. Por ejemplo, cuando se acciona un pulsador habilitado, genera unevento Press que, a continuación, el programa puede manejar.

Puede que no desee que se habilite un componente hasta que exista una ciertacondición. En caso del pulsador, puede que desee que el usuario pueda pulsarlosólo cuando se ha seleccionado un elemento en un recuadro de lista.

Cuando un componente no está habilitado, no responde a la interacción de usuarioy su etiqueta se atenúa.

Para habilitar un componente, establezca su valor de atributo Enabled en 1. Si nodesea que un componente esté habilitado, establezca este valor en 0.

Atributos de tamaño y posiciónPuede utilizar los atributos Height y Width para indicar el tamaño, en pixels, de lamayoría de componentes.

También puede utilizar los atributos Left, Bottom y Top para especificar laposición del componente en el componente que lo contiene (generalmente unaventana). El valor de posición también se expresa en pixels. Al posicionar uncomponente, los valores son relativos a la esquina superior izquierda.

Estos atributos son útiles porque cambian dinámicamente el tamaño y la posiciónde los componentes en tiempo de ejecución. Por ejemplo:v Si un usuario puede cambiar el tamaño de una ventana, puede que desee

codificar una subrutina de acción que maneje el evento ReSize y altere la

CSRN01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEq..*

C 'ST1' setatr '000:000:128' 'BackMix'

Capítulo 5. Atributos comunes 37

Page 56: c 0924494

posición de los componentes en esa ventana, de manera que sigan centradosdentro de la misma. Si no lo hace, los componentes seguirán siendo relativos ala esquina superior izquierda de la ventana.

v Si la aplicación se ejecuta en sistemas que utilizan monitores con resolucionesdiferentes, puede utilizar los atributos del sistema %DspWidth y %DspHeightpara asegurar que las ventanas sean visibles sin importar la resolución depantalla. Puede que desee situar la ventana en el centro de la pantalla o en otracoordenada.

Éste es un cálculo que puede realizarse en el evento Create para una ventana. Esteejemplo calcula las coordenadas adecuadas para centrar una ventana denominadaWindow1 y luego mueve la ventana a una nueva coordenada antes de visualizarlaen la pantalla.

Atributo VisiblePuede utilizar el atributo Visible para especificar cuándo desea que se visualice uncomponente o una ventana. Por ejemplo, puede que desee que aparezca unpulsador en la pantalla solamente en tiempo de ejecución. Para ello, al crear elpulsador en el Diseñador GUI, vaya al cuaderno de propiedades del componente ydesactive el distintivo de visible. Luego, en tiempo de ejecución, establezca el valorde atributo Visible en 1 cuando desee que aparezca el pulsador.

Atributo FocusEl área de una ventana donde un usuario puede interactuar con la interfaz tiene elfoco de entrada. El componente que tiene el foco de entrada debe habilitarse pararesponder a las acciones del usuario, tales como pulsar una tecla o un botón.

*DName+++++++++++ETDsFrom+++To/L+++IDc.Keywords+++++++++++++++++++++++++** Declarar atributos de sistema de tamaño de pantalla

D%DspHeight S 4P0D%DspWidth S 4P0*

CSRN01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEq** Manejar evento de crear para Window1.* Obtiene tamaño de pantalla y calcula coordenadas de pixels* para situar la ventana en el centro de la pantalla.*

C WINDOW1 BEGACT CREATE WINDOW1** Obtener dimensiones de las ventanas:

C 'Window1' GETATR 'Width' winWidth 4 0C 'Window1' GETATR 'Height' winHeight 4 0** Calcular nuevas coordenadas para centrar la ventana

C %DspWidth SUB winWidth newLeft 4 0C %DspHeight SUB winHeight newBottom 4 0C newLeft DIV 2 newLeftC newBottom DIV 2 newBottom** Centrar la ventana y hacerla visible

C 'Window1' SETATR newLeft 'Left'C 'Window1' SETATR newBottom 'Bottom'C 'Window1' SETATR 1 'Visible'C ENDACT*

38 Programación con VisualAge RPG

Page 57: c 0924494

Hay ocasiones en que deseará que el foco esté en un componente del programapara que el usuario pueda utilizarlo de inmediato. Por ejemplo, si marca varioscampos de entrada y requiere que el usuario vuelva a entrar información en uncampo de entrada en particular, establecerá el valor de atributo de Focus en 1 paraese campo de entrada. Cuando establezca el atributo, el cursor aparecerá en ellugar donde el usuario pueda empezar a escribir datos en el campo de entrada.

Además de proporcionar un foco a un componente concreto, puede determinar siun componente ha obtenido el foco. Un componente obtiene el foco cuando elusuario lo selecciona, avanzado hasta el mismo con el tabulador o seleccionándolocon el ratón. Cuando esto ocurre, se genera un evento GotFocus para elcomponente. Y viceversa, se genera un evento LostFocus cuando un componentepierde el foco.

Atributo UserDataTodos los componentes soportan el atributo UserData. Utilice este atributo paraasignar cualquier serie de texto a un componente. Esta serie no tiene efecto en elvalor de cualquier otro atributo del componente y no se visualiza. El atributoUserData puede contener un máximo de 65.535 caracteres.

Atributo LabelVarios componentes tienen un atributo Label. Es texto descriptivo que explica elpropósito del componente. El texto que aparece en un pulsador es un ejemplo deeste atributo.

Los siguientes componentes tienen un atributo Label:v Recuadro de selecciónv Contenedorv Recuadro de grupov Elemento de menúv Pulsadorv Botón de selecciónv Texto estáticov Ventanav Ventana con lienzo

Sustitución de etiquetaPuede sustituir el texto de una etiqueta utilizando un símbolo cuando establezcalos atributos Label, TabLabel o InfoLabel. Esto es particularmente útil si estádesarrollando aplicaciones para utilizarlas con otros idiomas, porque le permitetraducir las etiquetas y los mensajes que ha definido en el Diseñador GUI.

Cuando especifique la sustitución de etiquetas para un componente, se realizaráuna entrada en el archivo de mensajes del componente. Varios componentespueden utilizar la misma sustitución de etiqueta (por ejemplo, |OK·). Se utiliza lamisma entrada de archivo de mensajes para todas las referencias.

Defina una etiqueta de sustitución para un componente en su cuaderno depropiedades, especificando una serie, sin blancos intercalados, precedida delsímbolo (|). Esto añade un mensaje al archivo de mensajes. SeleccioneProyecto→Definir mensajes... para invocar el editor de mensajes y añada el textode mensaje con que desea sustituir el atributo Label cuando se ejecute laaplicación.

Capítulo 5. Atributos comunes 39

Page 58: c 0924494

Consejos sobre la traducciónAl definir el tamaño de un componente en el Diseñador GUI que tendrá unaetiqueta de sustitución, tenga en cuenta que el texto traducido puede ser más largoque el original.

Si utiliza nemotécnicos, recuerde que el carácter nemotécnico puede ser diferentepara otros idiomas.

Puede tener más de un archivo de mensajes traducido en los subdirectorios detiempo de ejecución asignando distintas extensiones de archivo a cada uno. Porejemplo, la versión inglesa del archivo de mensajes compilado podría denominarseSAMPLE·ENG y la versión alemana, SAMPLE·GER. Puede indicar al usuario quecopie el archivo de mensajes correspondiente a SAMPLE·MSG antes de ejecutar laaplicación.

40 Programación con VisualAge RPG

Page 59: c 0924494

Capítulo 6. Utilización de transferencia de datos

En esta sección se describe cómo se puede utilizar la transferencia de datos paramanipular el valor de algunos componentes.

Nota: La transferencia de datos no está soportada para las aplicaciones Java.

Una situación de transferencia de datos habitualEl usuario selecciona un componente (denominado componente origen) con elratón, lo arrastra a otro componente (denominado componente destino) y suelta elbotón para soltar el valor en el componente destino. Esto transfiere informacióndesde el componente origen al componente destino, y entonces el componentedestino puede actuar sobre esa información.

Nota: El propio componente no se desplaza con la transferencia de datos. Es elvalor del componente que está transfiriéndose.

Componentes que soportan la transferencia de datosLa siguiente tabla lista los componentes que soportan la transferencia de datos ylos datos sobre los que actúa cada uno.

Tabla 4. Componentes VisualAge RPG que soportan la transferencia de datos

Componente Datos transferidos

Recuadro de combinación El valor de la porción de campo de entrada del recuadro decombinación, o el elemento seleccionado para un tipo delista desplegable de recuadro de combinación

Campo de entrada El valor del atributo Text

Recuadro de lista El elemento seleccionado

Subarchivo de mensajes El mensaje seleccionado

Edición de múltiples líneas El valor del atributo Text

Texto estático El valor del atributo Label

Habilitación de componentes para la transferencia de datosSi desea que un componente sea un componente origen, establezca el atributoDragEnable correspondiente en el valor 1; y si desea que sea un componentedestino, establezca el atributo DropEnable en el valor 1. Puede establecer estosatributos en el cuaderno de propiedades del componente o en el programa. Nopuede volver a establecer estos atributos durante el tiempo de ejecución: una vezque se habilita un componente para la transferencia de datos, permaneceestablecido.

Después de haber establecido los atributos DragEnable y DropEnable, puedearrastrar el componente origen y soltarlo en el componente destino. Esto hace quese produzca el evento Drop para el componente destino.

Nota: Los atributos DragEnable y DropEnable no están soportados en lasaplicaciones Java.

© Copyright IBM Corp. 1994, 2000 41

Page 60: c 0924494

Ejemplo de transferencia de datosEn el siguiente ejemplo, una ventana tiene dos campos de entrada denominadosEF1 y EF2. El atributo DragEnable se establece para EF1 y el atributo DropEnablese establece para EF2. Entonces, el valor de texto de EF1 puede arrastrarse ysoltarse en EF2.

El campo de entrada EF2 sólo permite ciertos valores. En el evento Drop para estecomponente, la subrutina de acción comprueba que el valor soltado es válido. Si elvalor no es válido, se añade un mensaje al componente subarchivo de mensajes.

********************************************************************** ** ID de program. : DragDrop ** ** Descripción . : Programa de ejemplo que muestra cómo responder ** al evento DROP y acceder a datos transferidos. ** ** Nota: Java no da soporte a la función arrastrar y soltar ** ************************************************************************ Definir el atributo de evento de datos DROP

D%Data S 5A********************************************************************** ** Ventana. . : MAIN ** ** Componente : PB_EXIT ** ** Evento . . : PRESS ** ** Descripción: Finalizar el programa ** ***********************************************************************

C PB_EXIT BEGACT PRESS MAIN*

C move *on *inlr*

C ENDACT

Figura 12. Código de ejemplo de arrastrar y soltar (Pieza 1 de 2)

42 Programación con VisualAge RPG

Page 61: c 0924494

********************************************************************** ** Ventana. . : MAIN ** ** Componente : EF2 ** ** Evento . . : DROP ** ** Descripción: Esta subrutina de acción obtendrá el control cuando ** se ha transferido un valor al campo de entrada EF2 ** Al comprobar el atributo de evento %Data, ** determinará si se permite el valor transferido para ** el campo de entrada y añadirá el mensaje ** correspondiente al componente subarchivo de ** mensajes. ** ***********************************************************************

C EF2 BEGACT DROP MAIN** Borrar el subarchivo de mensajes

C 'Msg1' setatr 0 'RemoveMsg'** Comprobar que el valor transferido está permitido*

C if %Data <> 'Yes ' andC %Data <> 'No ' andC %Data <> 'Maybe'*

C 'Msg1' setatr 1 'AddMsgID'C endif*

C ENDACT********************************************************************** ** Ventana. . : MAIN ** ** Componente : EF2 ** ** Evento . . : CHANGE ** ** Descripción: ** ***********************************************************************

C EF2 BEGACT CHANGE MAIN*

C ENDACT

Figura 12. Código de ejemplo de arrastrar y soltar (Pieza 2 de 2)

Capítulo 6. Utilización de transferencia de datos 43

Page 62: c 0924494

44 Programación con VisualAge RPG

Page 63: c 0924494

Capítulo 7. Utilización de componentes

Esta sección contiene sugerencias útiles acerca de la utilización de los componentesde VisualAge RPG. La descripción de cada componente contiene una lista de losatributos y eventos que se aplican al componente. Los siguientes componentes sedescriben detalladamente.v “ActiveX” en la página 46v “Control de animación” en la página 50v “Calendario” en la página 51v “Lienzo” en la página 53v “Recuadro de selección” en la página 55v “Recuadro de combinación” en la página 57v “Referencia a componente lógico” en la página 62v “Contenedor” en la página 64v “Cliente DDE” en la página 71v “Campo de entrada” en la página 72v “Gráfica” en la página 75v “Pulsador gráfico” en la página 77v “Recuadro de grupo” en la página 79v “Barra de desplazamiento horizontal” en la página 80v “Imagen” en la página 81v “Bean Java” en la página 87v “Recuadro de lista” en la página 90v “Medios” en la página 99v “Panel de medios” en la página 101v “Barra de menús” en la página 103v “Elemento de menú” en la página 104v “Subarchivo de mensajes” en la página 106v “Edición de múltiples líneas” en la página 110v “Cuaderno” en la página 115v “Página de cuaderno” en la página 116v “Página de cuaderno con lienzo” en la página 117v “Interfaz ODBC/JDBC” en la página 118v “Recuadro de contorno” en la página 131v “Menú emergente” en la página 132v “Barra de progreso” en la página 133v “Pulsador” en la página 134v “Botón de selección” en la página 136v “Graduador” en la página 139v “Selector cíclico” en la página 145v “Texto estático” en la página 149v “Barra de estado” en la página 151v “Subarchivo” en la página 152v “Submenú” en la página 166v “Temporizador” en la página 167v “Barra de desplazamiento vertical” en la página 174v “Ventana” en la página 175v “Ventana con lienzo” en la página 176v “*Component” en la página 184

Nota: Los componentes no se presentan en el orden en que debe utilizarlos. Debeutilizar el componente ventana o el componente ventana con lienzo en

© Copyright IBM Corp. 1994, 2000 45

Page 64: c 0924494

primer lugar para iniciar la construcción de la aplicación y luego paraañadir otros componentes a medida que sea necesario.

Si desea obtener más información acerca de los atributos de componente, eventos yatributos de evento, puede consultar el tema VisualAge RPG Manual de consulta decomponentes. Para aprender consejos de programación adicionales, vea el“Capítulo 3. Programación con componentes” en la página 25.

ActiveX

* Restricción: Este componente no está soportado en las aplicaciones Java.

Utilice el componente ActiveX para añadir objetos de control ActiveX al proyecto.Las aplicaciones podrán acceder a los atributos y supervisar los eventos. (Otrosproveedores se encargan del desarrollo y suministro de los controles ActiveX.)

Debe estar familiarizado con los controles ActiveX que añade. El Diseñador GUI deVARPG no puede controlar las funciones que proporcionan estos componentes.

Nota: VARPG sólo trabaja con controles ActiveX que tengan interfaces escritas enC++. Consulte con su suministrador de controles ActiveX para asegurarse deque VARPG funcionará con el control ActiveX que desea utilizar.

46 Programación con VisualAge RPG

Page 65: c 0924494

Atributos de componente

Activate AddEvent Bottom DeActivateHasPrpPage Height Left MethodOCXProp OCXValue ParentName PartNamePartType Refresh RmvEvent ShowPropTop UserData Visible Width

Eventos a los que puede aplicarse

Create Destroy OCXEvent

Adición de controles ActiveXPara añadir un control ActiveX al proyecto, pulse el componente ActiveX en lapaleta de componentes. Pulse el puntero del ratón en el lugar de la ventana dediseño en el que desea colocar el componente ActiveX. Aparecerá un diálogoInsertar objeto. Seleccione el control ActiveX con el que desea trabajar.

Un control ActiveX puede contener propiedades, métodos y eventos que unprogramador puede manipular, llamar y responder respectivamente. El términocontrol ActiveX hace referencia al componente ActiveX real que se está utilizando.Ejemplos de ellos son un control de gráfico, calendario u hoja de cálculo. Eltérmino componente ActiveX hace referencia al componente ActiveX que seencuentra en la paleta de componentes de VARPG.

Establecimiento de propiedadesPuede establecer las propiedades de un control ActiveX en tiempo de construccióno ejecución. Para establecer propiedades durante el tiempo de construcción, abra elcuaderno de propiedades del componente ActiveX en la ventana de diseño. Pulsecon el botón derecho del ratón en el icono de ActiveX en la ventana de diseño yseleccione Propiedades. Si está disponible un editor de propiedades para el controlActiveX, también se visualizará. A continuación, puede editar directamente losvalores de las propiedades.

Las propiedades, métodos y eventos del control ActiveX aparecen en la páginaInformación del cuaderno de propiedades del componente ActiveX. Seleccione elbotón de selección apropiado para ver las opciones disponibles.

El establecimiento u obtención de una propiedad durante el tiempo de ejecuciónrequiere dos pasos. En primer lugar, establezca el atributo OCXProp delcomponente ActiveX en la propiedad Name del control ActiveX que estáutilizando. Utilice el atributo OCXValue para establecer u obtener la propiedad.

El siguiente ejemplo establece la propiedad Depth de un control de diagramacircular ActiveX:C 'PieChart' Setatr 'Depth' 'OCXProp'C 'PieChart' Setatr DepthValue 'OCXValue'

Nota: El atributo OCXValue toma un valor de tipo serie. El tiempo de ejecución deVisualAge RPG manejará las conversiones adecuadas antes de reenviar elvalor al control ActiveX.

Capítulo 7. Utilización de componentes 47

Page 66: c 0924494

Llamada a métodosEl IDE de VisualAge para RPG intenta compilar una lista de métodos disponiblespara el control ActiveX. Esta lista está disponible en la página Información delcuaderno de propiedades del componente ActiveX. Para cada método, losparámetros se muestran entre corchetes que contienen IN para un parámetro deentrada, OUT para un parámetro de salida o nada si no se dispone de información.

Nota: Quizás no sea posible para el constructor descubrir todos los métodosdisponibles del control ActiveX. Consulte la documentación del control paraobtener una lista completa.

La llamada a los métodos de un control ActiveX se realiza en tiempo de ejecuciónestableciendo el atributo Method del componente ActiveX. El atributo Methodtoma un valor de tipo serie que contiene el nombre del método, seguido de cero omás valores de parámetro separados mediante una coma. La sintaxis es:nombre_método, valor1, valor2, ...

El siguiente ejemplo llama al método AboutBox de un control de gráfico circularActiveX. El método no utiliza parámetros.C 'PieChart' Setatr 'AboutBox' 'Method'

El siguiente ejemplo llama al método AddData de un control de gráfico circularActiveX. Este método acepta dos parámetros: una etiqueta de tipo serie y un valorde tipo flotante.D datax C const('AddData, ItemX, 3.0')

C 'PieChart' Setatr datax 'Method'

48 Programación con VisualAge RPG

Page 67: c 0924494

Respuesta a eventosVisualAge RPG puede responder a todos los eventos generados por el controlActiveX que se está utilizando. VisualAge para RPG acepta los eventos del controlActiveX como un OCXEvent. Puede utilizar el evento %RealName para recuperarel nombre real del evento.

Para recibir un evento desde un control ActiveX, primero debe registrar el eventoen el tiempo de ejecución de VisualAge RPG. Establezca el atributo AddEvent delcomponente ActiveX en el nombre de tipo serie del evento que debe recibirse.También puede establecer el atributo AddEvent en *ALL para recibir todos loseventos que genere el control ActiveX. Para eliminar el registro de un evento,establezca el atributo RmvEvent en el nombre de tipo serie del evento.* Declarar el atributo del evento

D %RealName s 20a

* Registrar el evento en el tiempo de ejecución de VisualAge para RPGC 'DataQ' Setatr 'Click' 'AddEvent'

* Responder a OCXEventC DATAQ BEGACT OCXEVENT FRA000000BC if %RealName = 'Click'* Realizar las acciones oportunas

C endif

Capítulo 7. Utilización de componentes 49

Page 68: c 0924494

Control de animación

En las aplicaciones de Windows, el componente control de animación reproducelos archivos de vídeo con la extensión AVI. Este componente se distingue delcomponente medios en que el vídeo se reproduce independientemente de la lógicadel programa. Un uso habitual de este componente es visualizar un archivo AVIque muestre un progreso como, por ejemplo, un archivo que se traspasa de unacarpeta a otra.

El componente control de animación reproduce archivos de vídeo sin sonido. Elarchivo AVI no puede estar en formato comprimido a menos que se hayacomprimido con el método RLE (Running-Length Encoded).

En las aplicaciones Java, el componente control de animación se utiliza parareproducir una secuencia de archivos GIF utilizando el atributo NbrOfImage.

Atributos de componente

FileName FrameRate Handle* LeftMode NbrOfImage ParentName PartNamePartType Top UserData Visible

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy

50 Programación con VisualAge RPG

|

Page 69: c 0924494

Calendario

El componente calendario representa un calendario por meses. Al efectuar unapulsación sobre una de las flechas de los meses, el usuario puede navegar por elcalendario y desplazarse al mes anterior o posterior.

También tiene un control del programa absoluto sobre el calendario paradesplazarse hasta una fecha específica, determinar qué fecha ha seleccionado elusuario y añadir breves comentarios de texto a días individuales en el calendario.

Atributos de componente

Border Bottom ClearAll ClearDateClearMonth ClearYear Color ColorAreaColorMix Date DateIdx DateTextDateUnder Day DayIdx DayLenDayNumPos DayNumRect DayStart EnabledFontArea FontBold FontItalic FontNameFontSize FontStrike* FontUnder* FrmtStringHandle* Height HRule LeftMonth MonthArrow MonthIdx MonthLenOutlineRcl ParentName PartName PartTypeRefresh ShowRects ShowText TipTextTop UserData Visible VRuleWeekDay WeekDayIdx Width YearYearIdx YearLen

* Nota:: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Click Create Destroy DblClickMouseDown MouseEnter MouseExit MouseMoveMouseUp MthChange YearChange

Determinar la fecha que el usuario ha seleccionadoEl atributo DateUnder puede utilizarse para determinar sobre qué fecha seencuentra el puntero del ratón. En el siguiente ejemplo, la fecha se recuperacuando el usuario pulsa en el calendario. Fíjese que estamos comprobando que elvalor DateUnder no está en blanco. Esto es debido a que el evento click seproduce sin importar donde se encuentra el ratón. Si el ratón no está encima deuna fecha determinada, el atributo DateUnder estará en blanco.

Fíjese también que la fecha es devuelta como una cadena de caracteres en elformato AAAAMMDD:

Capítulo 7. Utilización de componentes 51

Page 70: c 0924494

Utilizar atributos de índice de fechaSe proporcionan varios atributos que le permiten acceder al calendario sin afectar alo que se está visualizando en ese momento. En este ejemplo, se añade uncomentario a un día determinado del calendario.

C 'Cal1' Getatr 'DateUnder' AAAAMMDDA 8** Si el ratón está sobre un día...

C If AAAAMMDDA <> *Blanks** Ponga la fecha en números

C Move AAAAMMDDA AAAAMMDD 8 0** Procese la fecha* ...* ...

C EndIf*

Figura 13. Ejemplo del componente calendario

** Establezca índice a la fecha para consulta

C 'Cal1' Setatr '19971210' 'DateIdx'** Establezca comentario del día

C 'Cal1' Setatr 'Vacation' 'DateText'*

Figura 14. Añadir un comentario

52 Programación con VisualAge RPG

Page 71: c 0924494

Lienzo

Utilice el componente lienzo con una ventana o una página de cuaderno si deseaincluir más de un componente en la ventana o en la página. Puede colocardiversos componentes en el lienzo señalándolos y pulsando el botón del ratón ycambiarlos de posición para crear una interfaz gráfica de usuario.

El componente lienzo ocupa el área de cliente de una ventana o de una página decuaderno. Si en la ventana o en la página de cuaderno no hay lienzo, sólo puedecolocar un componente en el área de cliente, a menos que sean extensiones de laventana, como barras de menús y subarchivos de mensajes.

A menudo creará ventanas y páginas de cuaderno que contendrán más de uncomponente. En este caso, deberá utilizar la página de cuaderno y la ventana conel componente lienzo. De este modo se ahorrará un paso, ya que estoscomponentes ya contienen el lienzo.

A la hora de construir, también puede incluir una imagen de bitmap a modo defondo del lienzo; para ello, especifique el atributo FileName. Esta imagen puedeponerse en mosaico estableciendo el atributo Tile. En las aplicaciones Java, puedeincluir imágenes GIF o JPG como fondo.

Notas:

1. Los componentes lienzo, ventana (sin lienzo) y página de cuaderno (sin lienzo)se encuentran en el catálogo de componentes, no en la paleta de componentes.Si va a utilizarlos con frecuencia, puede trasladarlos del catálogo a la paleta decomponentes.

2. Si los componentes situados en un componente lienzo tienen especificado elvalor de font por omisión (Font del sistema por omisión), heredarán la definiciónde font especificada en el componente lienzo. Para aplicar un font determinadoa la mayor parte de componentes de un lienzo, especifique ese font en elcomponente lienzo en lugar de hacerlo en cada componente individual.

Para obtener información relacionada, consulte el apartado:v “Ventana” en la página 175v “Ventana con lienzo” en la página 176v “Página de cuaderno” en la página 116v “Página de cuaderno con lienzo” en la página 117.

Capítulo 7. Utilización de componentes 53

Page 72: c 0924494

Atributos de componente

BackColor BackMix Bottom* EnabledFileName FontBold FontItalic FontNameFontSize FontStrike* FontUnder* Handle*Height Left ParentName PartNamePartType ReadOnly Refresh TileTop* UserData Width

* Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Click Create DblClick DestroyMouseDown MouseMove MouseUp Popup

54 Programación con VisualAge RPG

Page 73: c 0924494

Recuadro de selección

Utilice el componente recuadro de selección si desea que el usuario elija entre dosestados claramente diferenciados; por ejemplo, activado y desactivado.

Una etiqueta asociada con el recuadro de selección describe el valor del mismocuando se selecciona.

Normalmente, se utiliza un grupo de recuadros de selección para proporcionar unalista de opciones. El usuario puede seleccionar uno, varios o ningún recuadro. Lasopciones no se excluyen mutuamente; por lo tanto, al marcar un recuadro deselección, el resto de recuadros de selección de la ventana no resulta afectado. Sidesea que el usuario pueda seleccionar sólo una opción de un grupo de dos o más,es necesario utilizar botones de selección. Consulte el apartado “Botón deselección” en la página 136 para obtener más información.

Para definir el estado de un recuadro de selección, el usuario puede pulsar elbotón del ratón en el mismo, pulsar la barra espaciadora cuando el recuadro tengael foco o pulsar la tecla correspondiente al nemotécnico (si le ha asignado una).

Atributos de componente

AddLink* AllowLink* BackColor BackMixBottom Checked Enabled FocusFontBold FontItalic FontName FontSizeFontStrike* FontUnder* ForeColor ForeMixHandle* Height Highlight* LabelLeft ParentName PartName PartTypeRefresh RemoveLink* ShowTips TipTextTop UserData Visible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy MouseEnter MouseExitMouseMove Popup Select

Capítulo 7. Utilización de componentes 55

Page 74: c 0924494

Establecimiento del estado de un componente recuadro deselección

Establezca el atributo Checked en uno de los siguientes valores para describir elestado del recuadro de selección:

1 El recuadro de selección está establecido y el estado es activado.

0 El recuadro de selección no está establecido y el estado es desactivado.

El recuadro de selección contiene una marca de selección cuando su estado esactivado.

Establecimiento de un nemotécnico

Nota: Los nemotécnicos no están soportados en las aplicaciones Java.

Para especificar una clave nemotécnica para el recuadro de selección, coloque elidentificador nemotécnico delante de un carácter en la etiqueta del recuadro decomprobación. En Windows NT/95/98, se utiliza el símbolo &. Este carácter es laclave nemotécnica y se visualizará en la interfaz con un subrayado (por ejemplo,Visible). El subrayado informa a los usuarios que pueden seleccionar el recuadrode selección pulsando la tecla subrayada en el teclado.

Señalización de eventosCuando el usuario selecciona un recuadro de selección para activar o desactivar elestado, se señala un evento Select.

56 Programación con VisualAge RPG

Page 75: c 0924494

Recuadro de combinación

Un recuadro de combinación ofrece al usuario la opción de escribir informaciónespecífica o de seleccionarla en una lista de opciones utilizadas con frecuencia.

Consiste en un campo de entrada con un recuadro de lista asociado que presentauna lista de valores que el usuario puede seleccionar. Si el usuario selecciona unode estos valores, el valor aparecerá en el campo de entrada y sustituirá al texto quehubiese previamente. También puede escribir un valor, que no ha de coincidir conninguno de los que están en la lista, directamente en el campo de entrada.

Los recuadros de combinación tienen diferentes estilos. Puede seleccionar el estiloque desee en el cuaderno de propiedades del componente.

Para obtener información relacionada, consulte los apartados:v “Recuadro de lista” en la página 90v “Campo de entrada” en la página 72

Atributos de componente

AddItemEnd AutoScroll* BackColor BackMixBottom Case* Count DelimCharDeSelect* DragEnable* DropEnable* EnabledFieldExit FirstSel Focus FontBoldFontItalic FontName FontSize FontStrike*FontUnder* ForeColor ForeMix GetItemHandle* Height Index InsertItem*ItemKey Left ParentName PartNamePartType ReadOnly Refresh RemoveItemSearch* SearchType* Selected SelectItemSequence* SetItem SetTop* ShowtipsSizeToFit* Text TipText TopUseDelim UserData Visible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Capítulo 7. Utilización de componentes 57

Page 76: c 0924494

Eventos a los que puede aplicarse

Change Create Destroy Drop*DropDown* Enter GotFocus KeyPressLostFocus MouseEnter MouseExit MouseMovePopup Select VKeyPress

*Nota: Consulte la descripción del evento si desea saber cuáles son lasrestricciones.

Selección del tipo de recuadro de combinaciónEn el cuaderno de propiedades del recuadro de combinación, puede elegir el tipode recuadro de combinación que desea crear:

Recuadro de combinaciónVisualiza la parte de campo de entrada y la parte de recuadro de lista delrecuadro de combinación.

Recuadro de combinación desplegableVisualiza la parte de campo de entrada. La parte de recuadro de lista estáoculta hasta que se pulsa la flecha hacia abajo (↓).

Recuadro de combinación de lista desplegableVisualiza la parte de campo de entrada. La parte de recuadro de lista estáoculta hasta que se pulsa la flecha hacia abajo (↓). El campo de entrada noacepta texto; sólo se utiliza para visualizar la selección de la parte delrecuadro de lista.

Nota: Todos los tipos de recuadros de combinación soportan la operación arrastrardesde la parte de campo de entrada. Sólo el recuadro de combinación simplesoporta la operación arrastrar desde la parte de recuadro de lista. Todos lostipos soportan la operación soltar elementos en la parte de campo deentrada, no en la parte de recuadro de lista.

Adición y establecimiento de la secuencia inicial deelementos

Puede utilizar el cuaderno de propiedades del recuadro de combinación paracolocar una lista inicial de elementos en un recuadro de combinación en elmomento del diseño.

Por omisión, los elementos se visualizan en el recuadro de combinación en elorden en que se añaden. Si desea que se visualicen siguiendo un orden máspreciso, establezca el atributo Sequence en ascendente, descendente o índice, antesde añadirlos. Con ello, los elementos se ordenan según la secuencia de clasificaciónASCII a medida que se van añadiendo.

No puede utilizar el atributo Sequence para cambiar el orden de los elementos queya están en el recuadro de combinación.

Adición de elementos en tiempo de ejecuciónPuede insertar elementos en un recuadro de combinación en tiempo de ejecuciónmediante el atributo InsertItem. El orden en que los elementos se visualizan sedetermina mediante el atributo Sequence.

58 Programación con VisualAge RPG

Page 77: c 0924494

Actualización de elementos de una listaPuede actualizar elementos que ya están en la lista. Utilice el atributo Index paraindicar qué elemento desea cambiar y el atributo SetItem para especificar los datosmodificados.

Nota: El atributo SetItem vuelve a situar un elemento en su ubicación original enuna lista, sin importar el valor que se establezca en el atributo Sequence.Por ejemplo, si establece el atributo Sequence en orden ascendente antes derellenar el recuadro de combinación, los elementos aparecen en el recuadrode combinación en orden ascendente; sin embargo, si a continuaciónrecupera un elemento, cambia su valor y utiliza el atributo SetItem parasustituirlo en el recuadro de combinación, el elemento se inserta en lamisma posición que ocupaba anteriormente. Por consiguiente, la lista puedeestar o no en orden ascendente después del cambio.

Establecimiento del principio de la listaUtilice el atributo SetTop para especificar qué elemento la de lista debe aparecer enla parte superior del recuadro de combinación. El establecimiento de este elementono reordena los elementos en la lista; desplaza la lista de manera que el elementoque se selecciona se visualiza al principio de la lista, seguido de los elementos quevienen después.

Eliminación de elementosUtilice el atributo RemoveItem y el valor Index del elemento que desea eliminar.Los valores de Index comienzan en el 1. Cuando se elimina un elemento de lalista, todos los elementos que siguen al elemento eliminado ascienden una posiciónen la lista.

Si desea eliminar todos los elementos de la lista, especifique el valor 0 en Index.

Selección y deselección de elementosEl usuario puede seleccionar y deseleccionar elementos utilizando el ratón o elteclado. Puede seleccionar y deseleccionar elementos utilizando los atributosSelected y DeSelect en el programa. Antes de utilizar estos atributos, establezca elatributo Index.

Recuperación de un elemento seleccionado por usuarioCuando un usuario selecciona un elemento de la lista en un recuadro decombinación, el elemento se coloca en el campo de entrada. Puede utilizar elatributo Text para obtener el elemento. Además, puede utilizar el atributo FirstSelpara determinar el índice del elemento que se ha seleccionado.

Capítulo 7. Utilización de componentes 59

Page 78: c 0924494

El usuario también puede escribir un valor en la parte de campo de entrada delrecuadro de combinación. Este valor no tiene que ser necesariamente uno de losvalores de la lista. Si desea que el usuario pueda seleccionar sólo aquelloselementos que están en la lista, establezca el valor 0 en el atributo ReadOnly.

Puede utilizar el atributo Count para determinar si hay elementos que recuperar.

Utilización de clavesTanto el recuadro de lista como el recuadro de combinación le permiten añadirelementos a la lista que constan de una parte ″clave″ y de una parte de ″datos″.Cuando se añaden elementos a la lista, sólo se visualiza la parte de datos delelemento. Si el usuario selecciona un elemento, podrá recuperar mediante elprograma la parte clave del elemento.

Para habilitar las claves de una lista, deberá seleccionar el recuadro de selección’Utilizar separador’ en la página ″Separador″ del cuaderno de valores de loscomponentes y especificar un carácter separador. El carácter separador por omisiónes el punto y coma (;). Los elementos de la lista constan de la parte clave, seguidade un separador, seguida de la parte de datos. Por ejemplo:01;Envío

Como ejemplo, supongamos que desea mostrar una lista de departamentos en unalista que permita al usuario hacer una selección. En la base de datos, almacenarálos departamentos como un campo de 2 caracteres, sin embargo quiere que elusuario pueda ver la descripción. Deberá añadir los siguientes datos a la lista:v 01;Envíov 02;Fabricaciónv 03;Nóminasv 04;Distribución

Nota: Con el recuadro de combinación podrá añadir la lista por omisión en lapágina Datos de su cuaderno de valores.

Cuando el usuario hace una selección de la lista, podrá utilizar el siguiente códigopara obtener la parte clave del elemento.

C 'Combo1' Getatr 'FirstSel' X 2 0C 'Combo1' Setatr X 'Index'C 'Combo1' Getatr 'ItemKey' Key

60 Programación con VisualAge RPG

Page 79: c 0924494

Establecimiento del texto del campo de entradaCuando un recuadro de combinación se visualiza por primera vez, el campo deentrada está en blanco. Si desea colocar uno de los elementos de lista en el campode entrada, defina el valor del atributo SelectItem como el índice del elemento quese va a utilizar.

Señalización de eventosEl evento Select se señala cuando:v Un usuario selecciona un elemento que está en un recuadro de combinación.v Se selecciona un elemento de la lista en el programa.v El usuario selecciona un elemento que ya ha sido seleccionado.

El evento Enter se señala cuando:v El usuario efectúa una doble pulsación sobre un elemento que está en el

recuadro de combinación.v Se pulsa la tecla Intro cuando el recuadro de lista tiene el foco y se ha

seleccionado un elemento.

En la subrutina de acción de estos eventos, puede utilizar el atributo Selected paradeterminar qué elemento se ha seleccionado.

Capítulo 7. Utilización de componentes 61

Page 80: c 0924494

Referencia a componente lógico

El componente referencia a componente lógico permite que un componente lógicode VARPG se comunique con otro. Utilice el componente referencia a componentelógico para afectar a un componente del otro componente lógico. El componentelógico al que se hace referencia debe estar ejecutándose en la misma aplicación queel componente referencia a componente lógico.

El componente referencia a componente lógico también supervisa un eventoespecificado en el otro componente lógico. Cuando se produce el eventosupervisado, el componente referencia a componente lógico señala un eventoNotify.

Atributos de componente

AddSrcEvt AttrValue Bottom CompNameLeft NotSrcEvt NotSrcPart NotSrcWinParentName PartName PartType RefAttrRefParent RefPart RmvSrcEvt UserDataVisible

Eventos a los que puede aplicarse

Create Destroy Notify

Referencia a atributos de componente en otros componenteslógicos

Hay dos métodos que puede utilizar para hacer referencia a un atributo de uncomponente en otro componente lógico:1. Definir el atributo en el cuaderno propiedades del componente referencia a

componente lógico.2. Establecer los atributos de componente referencia a componente lógico en

tiempo de ejecución.

Para poder hacer referencia a atributos de componente en otro componente lógico,debe asegurarse de que está ejecutándose el otro componente lógico. Utilice elcódigo de operación START para iniciar otro componente lógico.

El siguiente fragmento de código muestra cómo un componente referencia acomponente lógico en un componente lógico puede cambiar el valor de un atributode componente en otro componente lógico. En este ejemplo, el atributo FileNamede un componente imagen (IMG1) en la ventana WIN01 del componente lógicoCOMPB se actualiza con un nuevo valor.

62 Programación con VisualAge RPG

|

|

Page 81: c 0924494

Supervisión de eventos en otro componente lógicoPuede utilizar el componente referencia a componente lógico en un componentelógico para supervisar un evento que se produce en otro componente lógico que seejecuta en la misma aplicación. Defina el evento a supervisar en el cuaderno depropiedades del componente referencia a componente lógico, o en tiempo deejecución estableciendo los atributos adecuados. Cuando se produce el evento queestá supervisándose en el otro componente lógico, el componente referencia acomponente lógico señala un evento Notify.

El siguiente fragmento de código muestra cómo puede establecerse en tiempo deejecución un componente referencia a componente lógico para un evento en otrocomponente lógico. En este ejemplo, el evento que está supervisándose es el eventoPress para un pulsador denominado PB1 en la ventana WIN01 del componentelógico COMPB.

** Cambiar el bitmap para el componente imagen IMG1 en* la ventana WIN01 del componente lógico COMPB

C 'CR1' Setatr 'COMPB' 'CompName'C 'CR1' Setatr 'WIN01' 'RefParent'C 'CR1' Setatr 'IMG1' 'RefPart'C 'CR1' Setatr 'FILENAME' 'RefAttr'C 'CR1' Setatr 'D:\PIC.BMP' 'AttrValue'*

** Supervisar el evento PRESS del pulsador* PB1 de la ventana WIN01 del componente COMPB

C 'CR1' Setatr 'COMPB' 'CompName'C 'CR1' Setatr 'PRESS' 'NotSrcEvt'C 'CR1' Setatr 'PB1' 'NotSrcPart'C 'CR1' Setatr 'WIN01' 'NotSrcWin'*

Capítulo 7. Utilización de componentes 63

Page 82: c 0924494

Contenedor

Utilice el componente contenedor para almacenar registros relacionados. Losregistros se pueden mostrar en una vista de iconos, de árbol, de árbol de texto o dedetalles.

Atributos de componente

AddRcd Arrange BackColor BackMixBlankChar Bottom ChildCount ChildListCollapsed ColNumber Count DeSelectEditItem Enabled ExtSelect* FirstSelFocus FontBold FontItalic FontNameFontSize FontStrike* FontUnder* ForeColorForeMix GetNewID GetRcdFld GetRcdIconGetRcdText Handle* Height InUse*Label Left MiniIcon ParentIdParentList ParentName PartName PartTypeReadOnly RecordID Refresh RemoveRcdSelected SelectRcd SetRcdFld SetRcdIconSetRcdText SetTop* ShowTips SortAscSortDesc TipText Top UserDataView* Visible VisTitle VisTitlSepWidth

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Click Collapsed ColSelect CreateDblClick Destroy Enter ExpandedGotFocus KeyPress LostFocus MouseDownMouseEnter MouseExit MouseMove MouseUpPopup Select VKeyPress

Adición de columnas a un contenedorEn una vista de detalle, un registro corresponde a una fila en el componentecontenedor, y cada columna en esa fila corresponde a un campo en ese registro.Antes de añadir un registro a un contenedor, debe añadir las columnas necesariaspara visualizar los campos mediante el cuaderno de propiedades del componentecontenedor.

Tiene que especificar cuál de los siguientes cuatro tipos de columnas desea crear:

Texto de objetoUna columna de texto de objeto visualiza el texto descriptivo que seespecifica cuando se crea el registro. Puede cambiar el texto en tiempo deejecución con el atributo SetRcdText. Los usuarios pueden cambiar este

64 Programación con VisualAge RPG

|

Page 83: c 0924494

texto en tiempo de ejecución pulsando la tecla Alt y seleccionando elcampo con el ratón. Para obtener el valor de esta columna, utilice elatributo GetRcdText.

Icono de objetoUna columna de icono de objeto visualiza el archivo de icono que seespecifica cuando se crea el registro. Puede cambiar el nombre de archivode icono en tiempo de ejecución mediante el atributo SetRcdIcon.

Texto El texto es una serie que contiene información adicional. Una columna detexto puede contener cualquier serie de caracteres. El texto no puedecontener espacios en blanco. Si desea que aparezca un blanco en tiempo deejecución, utilice en la serie el carácter de subrayado ( _ ). Utilice elatributo SetRcdFld para cambiar este texto en tiempo de ejecución. Losusuarios pueden cambiar el texto en tiempo de ejecución pulsando la teclaAlt y seleccionando el campo con el ratón. Para obtener el valor de estacolumna, utilice el atributo GetRcdFld.

Icono Un icono muestra información de registro gráfico adicional. Una columnade icono visualiza un archivo de icono. Utilice SetRcdIcon para cambiar elnombre del archivo de icono en tiempo de ejecución.

Puede añadir un máximo de veinte columnas a un componente contenedor. Deellas, quince como máximo pueden ser una combinación de texto de objeto y decolumnas de texto, y cinco como máximo pueden ser de icono de objeto y deicono. Tenga en cuenta que, en Windows, sólo la primera columna puede contenerun icono.

El número de columnas y de tipos de columna no puede cambiarse en tiempo deejecución. Si añade registros que tienen más campos que el número de columnasen el contenedor, se pasan por alto los campos extra.

Adición de registros a un contenedorEn el código, utilice el atributo AddRcd para añadir registros a un contenedor. Esteatributo es una serie que consta de lo siguiente:

ID Texto NombreArchivo IDPadre {datos_campo datos_campo ...}

Los blancos se utilizan como delimitadores. Los parámetros son:

ID Un valor numérico exclusivo que se da a un registro. Este número debe sermayor que cero. Para asegurarse de que se asigna un ID exclusivo a cadaregistro que se cree, utilice el atributo GetNewID.

Texto El texto que se visualiza con el icono de objeto. Puede cambiarse en tiempode ejecución mediante el atributo SetRcdText.

FileNameEl nombre de un archivo que contiene la imagen de icono para unacolumna de icono de objeto. Este icono se visualiza en las vistas de iconosy de árbol del contenedor. Puede cambiar el nombre de archivo de iconoen tiempo de ejecución mediante el atributo SetRcdIcon.

ParentIDEl ID exclusivo del registro bajo el que aparecerá este registro. Si esteregistro no tiene un registro padre, coloque un 0 en este campo.

Datos_campoInformación adicional para un registro que se visualiza en una columna detexto o de icono. Cada valor de datos_campo actualiza la columna

Capítulo 7. Utilización de componentes 65

Page 84: c 0924494

correspondiente en el componente contenedor. Si desea tener una columnade contenedor de icono o de texto vacía, debe especificar un subrayado ( _) en el parámetro datos_campo.

El siguiente fragmento de código muestra los parámetros que se especifican paraañadir un registro de ejemplo a un contenedor. En este ejemplo no se añaden datosde columna.Utilice el atributo Count para determinar cuántos registros hay en un contenedor.

Actualización de columnas de contenedorUna vez que un registro se ha añadido a un contenedor, se visualizan los datos delos campos de registro en las columnas correspondientes del contenedor. Puedeactualizar datos en columnas de texto de contenedor individuales actualizando loscampos de registro.

Nota: Puede actualizar sólo los datos en las columnas; no puede cambiar elnúmero de columnas en el contenedor. El número de columnas se estableceal crear el contenedor en el Diseñador GUI.

Para actualizar una columna, establezca el atributo RecordID en el registro quecorresponde a esa columna, y establezca el atributo ColNumber en el campo enaquel registro que contiene los datos actualizados. El siguiente fragmento decódigo muestra cómo actualizar la tercera columna en un contenedor:

** No es un registro hijo

C Eval Parent = '0'** Utilizar texto de icono especificado en Diseñador GUI

C Eval IconText = '_'** Establecer nombre de archivo de icono a utilizar para este registro

C Eval IconFile = '.\\TOM.ICO'** Obtener nuevo ID de registro de contenedor y hacerlo de caracteres

C 'CT1' Getatr 'GetNewId' NextIDN 6 0C Move NextIDN NextID 6** Crear estructura de registro de contenedor

C Eval NextRcd = NextID + ' ' +C IconText + ' ' +C IconFile + ' ' +C Parent** Añadir el registro al contenedor

C 'CT1' Setatr NextRcd 'AddRcd'*

** Establecer id de registro al que hacer referencia

C 'CT1' Setatr NextIDN 'RecordID'** Hacer referencia a tercera columna del registro

C 'CT1' Setatr 3 'ColNumber'** Actualizar la columna con los nuevos datos

C 'CT1' Setatr 'Larry' 'SetRcdFld'*

66 Programación con VisualAge RPG

Page 85: c 0924494

Si desea que el nuevo valor de columna contenga blancos intercalados, utilice elcarácter de subrayado para representar cada blanco. Los caracteres de subrayado sesustituyen por blancos cuando se actualiza la columna. Por ejemplo:

Utilice el atributo GetRcdFld para recuperar el contenido de un campo de registro.Establezca el atributo RecordID en el ID exclusivo del registro y el atributoColNumber en el número de columna deseado.

Eliminación de registros de un contenedorUtilice el atributo RemoveRcd para eliminar registros de un componentecontenedor y para eliminar el ID de registro que identifica ese registro de maneraexclusiva. Para eliminar todos los registros del contenedor, establezca el valor ceroen el ID de registro.

El siguiente fragmento de código muestra cómo se elimina un registro de uncontenedor:

Cambio de la vista de contenedorPara cambiar la vista, utilice el atributo View. El componente contenedor puedevisualizar las siguientes vistas de los datos: iconos, árbol de iconos, árbol de textoy detalles.

Vista de iconosEn una vista de iconos, cada registro se representa mediante un icono con textopor debajo. Los registros hijos no se visualizan en la vista de iconos. Debeespecificar el nombre de archivo de icono y el texto descriptivo en la estructura deregistro cuando añada el registro al contenedor.

Puede cambiar el icono y el texto de icono en tiempo de ejecución utilizando losatributos SetRcdIcon y SetRcdText.

Para visualizar los iconos en filas en el contenedor, establezca el valor 1 en elatributo Arrange.

Para utilizar mini iconos, establezca el atributo MiniIcon en 1 o seleccione elrecuadro Mini icono de la página ’Estilo’ del cuaderno de propiedades.

** 'New data' se establece en la columna

C 'CT1' Setatr 'New_data' 'SetRcdFld'*

** Obtener ID del primer registro seleccionado

C 'CT1' Getatr 'FirstSel' TmpID 6 0** Si se ha seleccionado un registro, eliminarlo del contenedor

C If TmpID <> 0C 'CT1' Setatr TmpID 'RemoveRcd'C EndIf*

Capítulo 7. Utilización de componentes 67

Page 86: c 0924494

Vista de árbolEn una vista de árbol, los registros se presentan en forma jerárquica. La vista árbolde iconos muestra cada registro con su icono y el texto de icono a su lado. Si unregistro tiene registros hijos, se visualiza un signo más junto al icono. Alseleccionar el signo más se muestran todos los registros relativos a este registro. Elárbol de texto muestra registros de la misma forma que la vista de árbol de iconos,pero sólo en modalidad de texto, sin iconos.

Se dibujan líneas de conexión entre registros relacionados para mostrar su relación.

Figura 15. Ejemplo de vista de iconos

68 Programación con VisualAge RPG

Page 87: c 0924494

Vista de detallesEn una vista de detalles, los registros se muestran de uno en uno visualizándosecada columna (de manera similar a un subarchivo). Los registros hijos no sevisualizan en este tipo de vista.

Figura 16. Ejemplo de vista de árbol

Capítulo 7. Utilización de componentes 69

Page 88: c 0924494

Si el contenedor no es lo bastante grande para visualizar todos los registros a lavez, se añaden automáticamente barras de desplazamiento.

Para cambiar la vista, utilice el atributo View.

MiniiconosEsta opción permite al programador especificar si los iconos que hay dentro delcomponente contenedor se visualizarán como iconos normales o mini. Sólo afecta ala vista de iconos; las vistas de árbol y de detalles no sufrirán cambio alguno.

Figura 17. Ejemplo de vista de detalles

70 Programación con VisualAge RPG

Page 89: c 0924494

Cliente DDE

* Restricción: Este componente no está soportado en las aplicaciones Java.

Utilice el componente cliente DDE para intercambiar datos con otras aplicaciones(por ejemplo, hojas de cálculo), que den soporte al protocolo de intercambiodinámico de datos (DDE).

Este intercambio recibe el nombre de conversación DDE. La aplicación que iniciala conversación es el cliente y la aplicación que responde es el servidor. Paradeterminar si una aplicación da soporte a DDE, consulte la documentación que seha entregado con ella.

El componente cliente DDE da soporte a las conversaciones de enlace estático yenlace dinámico. Una conversación de enlace estático consta de un programacliente que realiza peticiones explícitas al programa servidor. Una conversación deenlace dinámico consta de un programa servidor que actualiza automáticamente elprograma cliente cuando se modifican sus datos.

Puede configurar conversaciones de enlace estático o dinámico en el cuaderno depropiedades del componente cliente DDE y en la lógica del programa.

Atributos de componente

AppName Bottom DDEAddLink DDEModeDDERmvLink Execute Format ItemLeft ParentName PartName PartTypePoke Request TimeOut TopTopic UserData Visible

Eventos a los que puede aplicarse

Create Data Destroy ExecuteAckPokeAck Terminate TimeOut

Capítulo 7. Utilización de componentes 71

Page 90: c 0924494

Campo de entrada

Utilice el componente campo de entrada si desea que el usuario pueda especificarvalores que no se pueden predecir. Un campo de entrada es un área en la que elusuario puede escribir o colocar texto. Sus límites suelen estar indicados. Elusuario puede desplazarse por el texto del campo de entrada si hay másinformación disponible de la que resulta visible.

Puede configurar el componente campo de entrada para que acepte datos de tipocarácter, numéricos o de doble byte (DBCS).

También puede hacer que el campo de entrada sea de sólo lectura, para que elusuario no pueda modificar la información que contiene directamente.

Puede señalar y pulsar un componente campo de entrada en la paleta decomponentes y después pulsar el botón del ratón en el componente subarchivopara crear un campo de entrada de subarchivo.

Atributos de componente

AddLink* Alignment AllowLink* AutoScroll*AutoSelect BackColor BackMix BottomCapsLock Copy CsrAtEnd CutDataType Delete DragEnable* DropEnable*Enabled FieldExit Focus FontBoldFontItalic FontName FontSize FontStrike*FontUnder* ForeColor ForeMix Handle*Height InsertMode* Left MaskedParentName PartName PartType PasteReadOnly Refresh RemoveLink* ShowTipsText TextEnd TextLength TextSelectTextStart TipText Top UserDataVisible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

72 Programación con VisualAge RPG

Page 91: c 0924494

Eventos a los que puede aplicarse

Change Click Create DblClickDestroy Drop GotFocus KeyPressLink* LostFocus MouseDown MouseEnterMouseExit MouseMove MouseUp PopupVKeyPress

*Nota: Consulte la descripción del evento si desea saber cuáles son lasrestricciones.

Utilización del atributo InsertModeEn Windows la modalidad de inserción siempre está activada. No puededesactivarse.

Utilización del atributo TextUtilice el atributo Text para obtener o establecer el valor de un campo de entrada.El campo que se utiliza para obtener o establecer el valor de un campo de entradadebe definirse como del mismo tipo que el campo de entrada. Por ejemplo, si estáobteniendo el valor de un campo de entrada numérico, el campo que recibe elvalor también debe definirse como numérico.

Obtención y establecimiento de información para una ventanaDurante la compilación, el compilador define de manera implícita los campos delprograma con el mismo nombre que el componente campo de entrada y con elmismo tipo de datos y longitud. Mediante los códigos de operación READ yWRITE con un nombre de ventana especificado en el factor 2, el valor del atributoText se copia automáticamente en estos campos o desde ellos. Los códigos deoperación READ y WRITE son muy útiles si se tienen muchos campos de entradaen la interfaz de usuario, para que no se tenga que establecer los atributos yobtener un valor de forma repetitiva.

Consulte el “Capítulo 3. Programación con componentes” en la página 25 si deseamás información.

Comprobación de validezPuede utilizar el cuaderno de propiedades para especificar que un campo deentrada sólo debe aceptar los datos que satisfagan los criterios que especifique.Para asegurar que los datos coinciden con ciertos valores, establezca los valores deCompare. Para asegurar que los datos están comprendidos en un intervalo devalores predefinidos, establezca los valores de Range.

Nota: VisualAge RPG utiliza el orden de clasificación ASCII para la comprobaciónde validez. En esto difiere del sistema AS/400, que utiliza el orden declasificación EBCDIC. Por consiguiente, los resultados pueden variar entrelos sistemas.

Para que se realice la comprobación de validez, debe tener por lo menos unpulsador o un pulsador gráfico en la ventana que tenga establecido el atributoValidate. Cuando se acciona el pulsador, se realiza la comprobación de validezpara cada campo de entrada que tenga definida la comprobación de validez. Si lacomprobación de validez es anómala en algún campo de entrada, se visualiza unaventana de mensaje y no se señala ningún evento de pulsar en el programa.

Capítulo 7. Utilización de componentes 73

Page 92: c 0924494

También puede utilizar el campo que hay en la parte superior del cuaderno depropiedades para establecer el mensaje que se visualizará si falla la comprobaciónde validez. Entre el texto del mensaje que ha de visualizarse o bien el nombre delarchivo de mensajes (como, por ejemplo, *MSG0001) que contiene el mensajecorrespondiente. Si se deja en blanco este texto, cuando falle la comprobación devalidez se visualizará el mensaje por omisión del sistema.

Nota: Este campo tiene un límite máximo de 15 caracteres.

Cómo evitar la entrada de datos por parte del usuarioPara evitar que el usuario entre datos en el campo de entrada, realice una de lasacciones siguientes:v Establezca el valor 1 en el atributo ReadOnly. Después de establecerlo, todavía

puede cambiar el valor del campo de entrada en el programa.v Establezca el valor 0 en el atributo Enabled. Después de establecerlo, el campo

de entrada no responde a eventos y el usuario no puede acceder al campo con eltabulador.

Enmascarado de los datos confidencialesSi el campo de entrada contiene datos confidenciales, como por ejemplo, unacontraseña o un número de cuenta, establezca el valor 1 en el atributo Masked.Una vez establecido, el carácter asterisco ( * ) aparece en el campo de entrada porcada carácter que se escribe. Los datos reales que se leen en el campo de entradano se ven afectados por ello.

74 Programación con VisualAge RPG

Page 93: c 0924494

Gráfica

El componente gráfica le permite crear y diseñar un gráfico en el proyecto.Durante la ejecución podrá enviar datos al gráfico y modificar los atributos degráfico y el tipo de gráfico. El componente gráfica da soporte a los tipos de gráficacircular, de líneas, de barras y de líneas y barras.

Los tipos de gráfica de barras y de líneas permiten utilizar el control de textoToolTip. Si está habilitado, al mover el ratón sobre un punto de datos se visualizael control de texto de ayuda flotante. Para utilizar este soporte en la lógica delprograma, debe establecer el valor del punto en el atributo TipText y activar elatributo ShowTips para la ventana que contiene el componente gráfica.

Atributos de componente

AutoInc BarLabel Bottom ColorColorArea ColorMix DataGroup DataPointDataValue Enabled FillStyle* FontAreaFontBold FontItalic FontName FontSizeFontStrike* FontUnder* GnEqGrpCol GnEqPntColGraphType GroupLabel GrphHiLite Handle*Height HitItem* HlitPoints* LabelPlaceLeft LegendType ParentName PartNamePartType Refresh StartNew TipTextTitle TitlePlace Top UnderPoint*UseData UserData Visible WidthXAxisLabel YAxisLabel YInc

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Click Create Destroy DblClickMouseDown MouseEnter MouseExit MouseMoveMouseUp

Enviar datos al gráficoAntes de enviar datos al gráfico deberá indicar qué DataGroup y qué DataPointva a recibir el valor. El atributo DataPoint representa el elemento posicional delgráfico que representa el valor. En un gráfico de barras, será una barra. En ungráfico de líneas, un punto, y en un gráfico circular, una de las porciones. Elatributo DataGroup es opcional. Este atributo indicar que existen grupos de datospara transformar en gráficos. El valor por omisión de DataGroup es uno. Alestablecer el atributo DataValue se establece el valor del elemento seleccionado.

Como ejemplo de un atributo DataGroup, supongamos que desea trazar lastemperaturas máxima y mínima de cada mes de un año determinado. Este gráficotendría dos grupos de datos. El primero representaría la temperatura mínima deun mes y el segundo la temperatura máxima de ese mes. Por lo que al gráfico serefiere, en primer lugar establezca el atributo DataGroup en 1. A continuación, en

Capítulo 7. Utilización de componentes 75

|

Page 94: c 0924494

un bucle, establezca el DataValue de todos los DataPoint en el valor de latemperatura mínima. Para completar el gráfico repita los mismos pasos para lastemperaturas máximas estableciendo DataGroup en 2.

Enviar datos al gráfico no lo actualiza. Deberá establecer el atributo UseData paravisualizar los datos.

El siguiente fragmento de código muestra cómo hacerlo:

Si se trata de un gráfico circular, cada grupo está representado en círculos distintos.

*C Do 2 Group 2 0C 'Graph1' Setatr Group 'DataGroup'*

C Do 12 Point 2 0C 'Graph1' Setatr Point 'DataPoint'*

C If Group = 1C 'Graph1' Setatr Low(Point) 'DataValue'*

C ElseC 'Graph1' Setatr High(Point) 'DataValue'C Endif*

C EndDo*

C EndDo*

C 'Graph1' Setatr 1 'UseData'

Figura 18. Enviar datos al gráfico

76 Programación con VisualAge RPG

Page 95: c 0924494

Pulsador gráfico

Utilice pulsadores gráficos para proporcionar un acceso fácil a las accionesutilizadas con frecuencia.

El pulsador gráfico proporciona la misma función que un pulsador. Indica unaacción que se iniciará cuando el usuario lo seleccione, pero en lugar de visualizaruna etiqueta que describa su función, muestra una imagen. El atributo FileNameespecifica el nombre de la imagen que debe utilizarse.

Los formatos válidos de imágenes de Windows son:v Bitmaps de Windows® y OS/2 (BMP, VGA, BGA, RLE, DIB, RL4, RL8)v Icono (ICO)v TIF, TIFF (Formato de Archivo de Imagen Codificada) de Microsoft/Aldusv GIF (Formato de Intercambio de Gráficos) de CompuServev PCX (Formato de Archivo de Imagen) de ZSoft PC Paintbrushv TGA, VST, AFI (Bitmap Targa/Vista) de Truevisionv IFF, ILBM (Formato de Bitmap Intercalado) de Amigav XBM (Bitmap) de X Windowsv PSE, PSEG, PSEG38PP, PSEG3820 (Segmento de Página de Impresora) de IBM

Los formatos válidos de imágenes Java son:v GIF (Formato de Intercambio de Gráficos) de CompuServev Formato Joint Photographic Experts Group (JPG, JPEG)

Para obtener información relacionada, consulte el apartado “Pulsador” en lapágina 134.

Capítulo 7. Utilización de componentes 77

Page 96: c 0924494

Atributos de componente

Bottom Enabled FileName FocusHandle* Height HelpEnable HighLightLeft ParentName PartName PartTypeRefresh ShowTips TipText TopUserData Validate Visible Width

* Nota:: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy GotFocus LostFocusMouseEnter MouseExit MouseMove PopupPress

Definición de la imagenPara definir la imagen que se visualiza en un pulsador gráfico, utilice el atributoFileName y especifique un nombre de archivo de bitmap (.BMP) o de icono (.ICO)válido. Debe almacenar los archivos de icono y de bitmap específicos del sistemaen el directorio de tiempo de ejecución adecuado. Si desea más información,consulte “Capítulo 12. Utilización de archivos de imágenes, de sonido y de vídeo”en la página 233.

Asignación de teclas de mandatoPuede asignar una tecla de mandato a un pulsador gráfico. Para hacerlo, abra elcuaderno de propiedades y seleccione una de las teclas de mandato de la listadisponible. Cuando el usuario pulsa la tecla de mandato en tiempo de ejecución,tiene el mismo efecto que si hubiese pulsado el botón de ratón o una tecla en elteclado. Un evento Press se señala en el programa.

Señalización de eventosCuando se acciona el pulsador, se señala un evento Press en el programa.

78 Programación con VisualAge RPG

Page 97: c 0924494

Recuadro de grupo

Utilice un recuadro de grupo para distinguir visualmente un grupo decomponentes de una ventana.

Un recuadro de grupo es un rectángulo trazado alrededor de un grupo decomponentes para indicar que están relacionados. Por lo general, es recomendableponer una etiqueta a un recuadro de grupo. Si no se precisa una etiqueta, puedeutilizar un recuadro de contorno.

Atributos de componente

Bottom Enabled FontBold FontItalicFontName FontSize FontStrike* FontUnder*ForeColor ForeMix Handle* HeightLabel Left ParentName PartNamePartType Refresh Top UserDataVisible Width

Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy

Etiquetado de un recuadro de grupoUtilice el atributo Label para especificar la serie que debe utilizarse para laetiqueta de recuadro de grupo.

Agrupación de botones de selecciónVea “Agrupación de botones de selección” en la página 136 para obtenerinformación relacionada.

Capítulo 7. Utilización de componentes 79

Page 98: c 0924494

Barra de desplazamiento horizontal

Utilice el componente barra de desplazamiento horizontal para poder desplazarsepor un panel de información de izquierda a derecha o viceversa. La informaciónpuede ser una lista de archivos, los registros de una base de datos, las columnas deun documento y otros elementos. Puede utilizar el atributo Range para representarel número total de los objetos por los que se efectuará el desplazamiento y elatributo PageSize para determinar el número de objetos que pueden visualizarseen una página.

Atributos de componente

Bottom Enabled Focus Handle*Height Left NextLine NextPagePageSize ParentName PartName PartTypePosition PrevLine PrevPage RangeTop UserData Visible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy Scroll

80 Programación con VisualAge RPG

Page 99: c 0924494

Imagen

Utilice el componente imagen para visualizar dibujos. El atributo FileNameespecifica el nombre de la imagen que debe utilizarse.

Los formatos válidos de imágenes de Windows son:v Bitmaps de Windows y OS/2 (BMP, VGA, BGA, RLE, DIB, RL4, RL8)v Icono (ICO)v TIF, TIFF (Formato de Archivo de Imagen Codificada) de Microsoft/Aldusv GIF (Formato de Intercambio de Gráficos) de CompuServev PCX (Formato de Archivo de Imagen) de ZSoft PC Paintbrushv TGA, VST, AFI (Bitmap Targa/Vista) de Truevisionv IFF, ILBM (Formato de Bitmap Intercalado) de Amigav XBM (Bitmap) de X Windowsv PSE, PSEG, PSEG38PP, PSEG3820 (Segmento de Página de Impresora) de IBM

Los formatos válidos de imágenes Java son:v GIF (Formato de Intercambio de Gráficos) de CompuServev Formato Joint Photographic Experts Group (JPG, JPEG)

Estos archivos residen en la estación de trabajo programable (PWS), no en elsistema principal. Debe almacenar los archivos de bitmap y de icono específicosdel sistema en el directorio de tiempo de ejecución adecuado (RT_JAVA oRT_WIN32) para que el programa de utilidad de empaquetado los incluya al crearel paquete de la aplicación.

Nota: El componente imagen sólo se puede soltar en una página de cuaderno conlienzo o en una ventana con lienzo.

Capítulo 7. Utilización de componentes 81

Page 100: c 0924494

Atributos de componente

AddLink* AllowLink* BackColor BackMixBorder Bottom Enabled FileNameHandle* Height Left MagnifyPanel ParentName PartName PartTypePrint Refresh RemoveLink* ShowTipsTipText Top UserData VisibleWidth

* Nota:: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Click Create DblClick DestroyLink* MouseEnter MouseExit MouseMove

* Nota:: Consulte la descripción del evento si desea saber cuáles son lasrestricciones.

Creación del componente de imagenEl componente imagen sólo puede crearse en un componente lienzo.

Establecimiento del nombre de archivoPara visualizar una imagen en el componente imagen, establezca el atributoFileName con el nombre del archivo que contiene la imagen. En aplicacionesWindows, el archivo debe contener una imagen de bitmap o icono válida. Enaplicaciones Java, el archivo debe contener una imagen GIF o JPG válida. Puedeque la imagen aparezca de manera diferente en estaciones de trabajo determinadasdependiendo del controlador de dispositivo de pantalla. Si especifica un nombrede archivo que no es válido, no se visualizará ninguna imagen. Puede borrar elcomponente imagen estableciendo el atributo FileName en blancos. Si obtiene unerror (como Archivo no encontrado) al utilizar el código de operación SETATR paraestablecer un nombre de archivo, se activa el indicador de error. Si desea másinformación, consulte “Capítulo 12. Utilización de archivos de imágenes, de sonidoy de vídeo” en la página 233.

Control del panel de ampliaciónPor omisión, se crea el componente imagen con un panel de ampliación. Puedeeliminar el panel de ampliación inhabilitándolo en el cuaderno de valores delcomponente imagen.

También puede habilitar o inhabilitar el panel de ampliación mediante el atributoPanel en el programa. Si establece el atributo Panel en 0, no se visualiza el panelde ampliación y puede mostrarse una parte mayor de la imagen. Si establece elatributo Panel en 1, se visualiza el panel de ampliación y queda menos espaciopara que se muestre la imagen.

Puede establecer la cantidad de ampliación en el programa. El valor de ampliaciónse representa con un porcentaje entre 25 y 200. Especificar un valor 0 dará comoresultado un ajuste mejor, en el que la imagen se ajustará en la ventana de imagenmientras se mantiene la constante de proporción entre horizontal y vertical.

82 Programación con VisualAge RPG

Page 101: c 0924494

Ejemplo de imagenEn este ejemplo, se lee un archivo del sistema AS/400. Cada registro del archivocontiene un campo de número de componente, que se inserta en el recuadro delista a medida que se lee cada registro. Cuando el usuario selecciona un número decomponente en el recuadro de lista y acciona el pulsador Ver, el número decomponente se concatena con la serie .BMP para formar un nombre de archivo.Entonces se utiliza el nombre de archivo para establecer el atributo FileName delcomponente imagen para visualizar la imagen. El atributo Label del componentetexto estático PINFO se actualiza para indicar el resultado de establecer el atributode nombre de archivo. Accione el pulsador Close para terminar el programa.

Capítulo 7. Utilización de componentes 83

Page 102: c 0924494

********************************************************************** ** ID de program. : IMAGE ** ** Descripción . : Ejemplo del componente imagen ** ** Este programa de ejemplo muestra cómo puede ** implementarse el componente imagen en VARPG ** Client. ** ** El ejemplo da por supuesto que hay un archivo ** en el sistema principal AS/400 denominado PARTS. ** Ese formato de archivo se compone de un campo ** denominado PARTNO. ** ** Cuando se inicie la aplicación, se invoca el ** evento Create para la ventana WIN1, que lee ** todos los registros del archivo e inserta el ** valor de campo PARTNO en el recuadro de lista LB1** ** Cuando el usuario accione el pulsador View, ** el nombre de archivo de imagen se construirá ** y se utilizará para establecer el atributo ** FILENAME del componente imagen IMG1. ** ***********************************************************************

H* Definir el archivo PARTS*

FPARTS IF E DISK REMOTE*

DPath C ''dnopic C 'Picture not available'*

Figura 19. Ejemplo en el que se utiliza el componente imagen (Pieza 1 de 3)

84 Programación con VisualAge RPG

Page 103: c 0924494

********************************************************************** ** Ventana . : WIN1 ** ** Componente : Close ** ** Evento . . : Press ** ** Descripción: Terminar el programa ** ***********************************************************************

C CLOSE BEGACT PRESS WIN1*

C move *on *inlr*

C ENDACT********************************************************************** ** Ventana . : WIN1 ** ** Componente : WIN1 ** ** Evento . . : Create ** ** Descripción: Esta subrutina de acción se ejecuta cuando se crea ** la ventana WIN1. ** Rellenará el recuadro de lista con los valores de ** número de componente del archivo PARTS. ** ***********************************************************************

C WIN1 BEGACT CREATE WIN1** Rellenar el componente recuadro de lista con elementos de la base* de datos

C read produc1 9999*

C *in99 doweq *offC 'LB1' setatr partno 'InsertItem'C read produc1 9999C enddo*

C ENDACT*

Figura 19. Ejemplo en el que se utiliza el componente imagen (Pieza 2 de 3)

Capítulo 7. Utilización de componentes 85

Page 104: c 0924494

********************************************************************** ** Ventana . : WIN1 ** ** Componente : VIEW ** ** Evento . . : PRESS ** ** Descripción: Visualizar la imagen para el componente seleccionado ** ***********************************************************************

C VIEW BEGACT PRESS WIN1** Obtener índice del elemento seleccionado

C 'LB1' getatr 'FirstSel' x 4 0** Si se ha seleccionado un elemento, construya el nombre de archivo* de bitmap

C x ifgt *zeroC 'LB1' setatr x 'Index'C 'LB1' getatr 'GETITEM' tmp20 20C movel tmp20 part 5C endif*

C move *blanks fullpath 64C move *blanks tmp64 64C path cat part:0 tmp64C tmp64 cat '.gif':0 fullpath** Establecer el nombre de archivo en el atributo FILENAME* de imagen para visualizar la imagen

C 'IMG1' setatr fullpath 'FILENAME' 80** Si el indicador 80 es "on", la operación de establecer el nombre* del archivo de imagen es fallida, es decir, no se ha encontrado el* archivo.* Establecer el atributo Label del componente de texto estático PINFO* para indicar el estado

C *in80 ifeq *onC 'PINFO' setatr nopic 'Label'*

C elseC 'PINFO' setatr *BLANKS 'Label'C endif*

C ENDACT*

Figura 19. Ejemplo en el que se utiliza el componente imagen (Pieza 3 de 3)

86 Programación con VisualAge RPG

Page 105: c 0924494

Bean Java

* Restricción: Este componente no está soportado en las aplicaciones Windows.

Utilice el componente bean Java para añadir beans JavaBeans® al proyecto. Losbeans Java sirven para llamar de forma directa a métodos Java. Si desea obtenermás información sobre las llamadas a métodos Java, consulte la publicación“Capítulo 18. Cómo invocar métodos Java desde programas VisualAge RPG” en lapágina 269.

Para desarrollar aplicaciones que utilicen el componente bean Java, debe tenerinstalado Java 2 Software Development Kit (J2SDK), Standard Edition, versión 1.2 osuperior, de JavaSoft, en la estación de trabajo. Si no tiene el J2SDK, puede bajarlode Sun Microsystems en el URL siguiente:http://www.javasoft.com/products/

Tras instalar el J2SDK, establezca la variable de entorno PATH de modo queapunte a la ubicación tanto del compilador Java como de jvm.dll, que forma partedel J2SDK y del JRE (Java Runtime Environment). Por ejemplo, si el directorioinicial de J2SDK es x:\jdk1.2, añada las siguientes sentencias en la variable PATH:x:\jdk1.2\bin

x:\jdk1.2\jre\bin\classic

Atributos de componente

AddEvent Bottom Enabled HeightLeft ParentName PartName PartTypeRmvEvent ShowProp Top UserDataVisible Width

Eventos a los que puede aplicarse

Create Destroy BeanEvent

Adición de beans al proyectoPara añadir un bean al proyecto, pulse el componente bean Java en la paleta decomponentes. Pulse el puntero del ratón en el lugar de la ventana de diseño en elque desea colocar el bean. Aparecerá un diálogo Abrir archivo. Seleccione elarchivo JAR que contiene el bean (o los beans) con el que desea trabajar. Apareceráuna ventana con una lista de todos los beans disponibles en el archivo JAR. Trasseleccionar un bean de la lista, se creará una instancia del bean. Se mostrará enuna ventana distinta junto con el diálogo de hojas de propiedades asociado y elpersonalizador de bean, si está disponible. (Puede modificar las propiedades delbean mediante el diálogo de hojas de propiedades y el personalizador de bean).

Para mostrar las propiedades, métodos y eventos de un bean, abra el cuaderno depropiedades del camponente bean Java en la ventana de diseño. Pulse con el botónderecho del ratón en el icono bean Java en la ventana de diseño y seleccione

Capítulo 7. Utilización de componentes 87

Page 106: c 0924494

Propiedades. Las propiedades, métodos y eventos de un bean aparecen en lapágina Información. Elija el botón de selección apropiado para ver las opcionesdisponibles.

No todos los eventos del bean se soportan. Los eventos soportados por VARPG semarcan con un asterisco (*) en la lista de Eventos.

Ubicación de los archivos JAR de beanTodos los archivos JAR relacionados con el bean del proyecto deben estar en eldirectorio de beans interno, x:\adtswin\beans, donde x:\adtswin es el directorioinicial en el que se ha instalado VARPG. Este directorio también debe incluir todoslos archivos JAR dependientes de bean. Por ejemplo, si el BeanA se encuentra enBeanA.jar y requiere los archivos de clases de beanclass.jar, tanto BeanA.jar comobeanclass.jar deben copiarse en el directorio de beans interno.

Mientras edita un proyecto, puede seleccionar un bean de un archivo JAR que nose encuentre en el directorio de beans interno. Este archivo JAR se copiará aldirectorio de beans interno tras construir el proyecto. No obstante, aún seguiráteniendo que copiar todos los archivos JAR dependientes del bean en estedirectorio.

Elimine todos los archivos JAR no utilizados del directorio de beans interno. Deeste modo se evitará la carga de archivos JAR innecesarios que no forman partedel proyecto.

Establecimiento de la classpath de JAREl programa de utilidad de empaquetamiento de VARPG no maneja laconfiguración de la classpath para los archivos JAR. Deberá establecer la variableclasspath de modo que incluya todos los archivos JAR que utilicen los beans delproyecto. Por ejemplo, si el BeanA utiliza BeanA.jar y depende de beanclasses.jar,debe establecer la classpath tal como se indica a continuación:SET CLASSPATH=x:\beandir\BeanA.jar;x:\beandir\beanclasses.jar;%CLASSPATH%;

donde x:\beandir es la vía de acceso de los archivos JAR del bean.

88 Programación con VisualAge RPG

Page 107: c 0924494

Establecimiento/Obtención de las propiedades del JavaBean einvocación de métodos

VARPG soporta la invocación directa de métodos Java. (Consulte el “Capítulo 18.Cómo invocar métodos Java desde programas VisualAge RPG” en la página 269para obtener más detalles). El tiempo de ejecución de VARPG proporciona unaclase accesora de Java para acceder a los objetos JavaBean de los proyectos. Laclase accesora, com.ibm.varpg.parts.VarpgBeanPart, se encuentra en el archivovarpg.jar. Esta clase le permite recuperar los objetos de bean cuyas instancias creael tiempo de ejecución de VARPG. Estos objetos de bean son componentes delproyecto de VARPG. El método para obtener el objeto de bean es:public static Object getBeanObject(String strComponentName,

String strParentName,String strPartName );

dondestrComponentName es el nombre del componente que contiene el componentede bean, strParentName es el nombre de la ventana que contiene el componente debean y strPartName es el nombre del componente de bean. El llamador debecomprobar las posibles referencias nulas que pueda devolver el método, paraasegurarse de que la llamada sea satisfactoria.

Para encontrar la especificación de método real para el establecimiento u obtenciónde las propiedades e invocación de métodos, consulte la documentación de losbeans que proporciona el proveedor o consulte la página Información del cuadernode propiedades del componente bean Java.

Capítulo 7. Utilización de componentes 89

Page 108: c 0924494

Recuadro de lista

Utilice el componente recuadro de lista para proporcionar al usuario una lista deelementos de los que se pueden seleccionar uno o más. Un recuadro de lista constade elementos de sólo lectura. Un elemento de un recuadro de lista es una serie decaracteres.

Las barras de desplazamiento verticales y horizontales permiten al usuario verpartes de la lista que no están visualizadas. Puede configurar el recuadro de listade modo que el usuario pueda seleccionar un solo elemento o varios. Puedeutilizar los atributos Search, SearchType y Case para buscar fácilmente en la listaun elemento determinado.

Atributos de componente

AddItemEnd AddLink* AllowLink* BackColorBackMix Bottom Case* CountDelimChar DeSelect DragEnable* DropEnable*Enabled ExtSelect* FirstSel FocusFontBold FontItalic FontName FontSizeFontStrike* FontUnder* ForeColor ForeMixGetItem Handle* Height IndexInsertItem* ItemKey Left MultSelectNbrOfSel ParentName PartName PartTypeRefresh RemoveItem RemoveLink* Search*SearchType* Selected SelectItem SelectListSequence* SetItem SetTop ShowTipsSizeToFit TipText Top UseDelimUserData Visible Width

* Nota:: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy Drop* Enter*GotFocus KeyPress LostFocus MouseEnterMouseExit MouseMove Popup SelectVKeyPress

* Nota:: Consulte la descripción del evento si desea saber cuáles son lasrestricciones.

Adición y establecimiento de la secuencia inicial deelementos

Por omisión, los elementos se insertan en un recuadro de lista en el orden en quese añaden. Si desea que se visualicen siguiendo un orden más preciso, establezca el

90 Programación con VisualAge RPG

Page 109: c 0924494

atributo Sequence en ascendente, descendente o índice, antes de añadirlos. Conello, los elementos se ordenan según la secuencia de clasificación ASCII a medidaque se van añadiendo.

No puede utilizar el atributo Sequence para cambiar el orden de los elementos queya están en el recuadro de lista.

Adición de elementos en tiempo de ejecuciónPuede insertar elementos en un recuadro de lista en tiempo de ejecución medianteel atributo InsertItem. El orden en que los elementos se visualizan se determinamediante el atributo Sequence.

Actualización de elementos de una listaPuede cambiar elementos que ya están en la lista. Utilice el atributo Index paraindicar qué elemento desea cambiar, y el atributo SetItem para especificar losdatos modificados.

Nota: Cuando un elemento se cambia utilizando el atributo SetItem, el elementopermanece en su ubicación original, sin importar el valor del atributoSequence. Por ejemplo, si estableció el atributo Sequence en ordenascendente cuando creó la lista, los elementos aparecen en el recuadro delista en orden ascendente; sin embargo, si a continuación recupera unelemento, cambia su valor y utiliza el atributo SetItem para sustituirlo en elcuadro de lista, el elemento se inserta en la misma posición en la que estabaantes. Por consiguiente, la lista puede estar o no en orden ascendentedespués del cambio.

Establecimiento del principio de la listaUtilice el atributo SetTop para especificar qué elemento de la lista debe aparecer enla parte superior del recuadro de lista. Al establecer este elemento se desplaza lalista. Cambia la visualización en el recuadro de lista, pero no reordena loselementos en la lista.

Eliminación de elementosUtilice el atributo RemoveItem para eliminar elementos de la lista. Utilice el valorde índice para especificar el elemento que va a eliminarse. Los valores de Indexcomienzan en el 1. Cuando se elimina un elemento de la lista, todos los elementosque siguen al elemento eliminado ascienden una posición en la lista.

Para eliminar todos los elementos de la lista, especifique un valor de Index de 0.

Selección y deselección de elementosEl usuario puede seleccionar o deseleccionar elementos utilizando el ratón o elteclado. Puede seleccionar y deseleccionar elementos estableciendo los atributosSelected y DeSelect en el programa. Para utilizar estos atributos, establezcaprimero el atributo Index.

Tipos de selecciónPuede utilizar atributos para especificar cómo se seleccionan los elementos en unrecuadro de lista. Están disponibles la selección única, múltiple y ampliada.

Selección únicaLa selección única (el valor por omisión) sólo permite que se seleccione un

Capítulo 7. Utilización de componentes 91

Page 110: c 0924494

elemento de una lista a la vez. Si un elemento ya está seleccionado, sedeseleccionará cuando se seleccione otro elemento.

Selección múltipleEl usuario puede seleccionar cualquier número de objetos o no seleccionarninguno.

Selección ampliadaEste tipo de selección es el adecuado para la selección de un sólo objeto,pero si es necesario el usuario puede ampliar la selección a más de unobjeto.

Recuperación de elementos de la listaPara recuperar un elemento de un recuadro de lista, utilice el atributo GetItem.Primero establezca el atributo Index para indicar qué elemento desea recuperar.

Normalmente recupera elementos de la lista que ha seleccionado el usuario. Paradeterminar qué elementos de un recuadro de lista se han seleccionado, utilice elatributo FirstSel o Selected. El atributo FirstSel devuelve el valor de índice delprimer elemento seleccionado de la lista. Si tiene que comprobar elementosseleccionados adicionales, asegúrese de que utiliza el atributo DeSelect paradeseleccionar este elemento; de lo contrario, el atributo FirstSel devuelve el mismoelemento.

Para determinar si se ha seleccionado un elemento específico, utilice el atributoSelected. El atributo Selected utiliza el valor de atributo Index para determinar sise ha seleccionado ese elemento.

Puede utilizar el atributo Count para determinar si hay elementos que recuperar.

Utilización de las teclasTanto el recuadro de lista como el recuadro de combinación le permiten añadirelementos a la lista que constan de una parte ″clave″ y de una parte de ″datos″.Cuando se añaden elementos a la lista, sólo se visualiza la parte de datos delelemento. Si el usuario selecciona un elemento, podrá recuperar mediante elprograma la parte clave del elemento.

Consulte el apartado Utilización de claves en la descripción del componenterecuadro de combinación para obtener más información.

Señalización de eventosEl evento Select se señala cuando:v Un usuario selecciona un elemento que está en un recuadro de lista.v Se selecciona un elemento de la lista en el programa.v El usuario selecciona un elemento que ya ha sido seleccionado.

El evento Enter se señala cuando:v Un usuario efectúa una doble pulsación sobre un elemento que está en el

recuadro de lista.v Un usuario pulsa la tecla Intro cuando el recuadro de lista tiene el foco y se ha

seleccionado un elemento.

En la subrutina de acción para estos eventos, puede utilizar el atributo Selected oFirstSel para determinar qué elemento se ha seleccionado.

92 Programación con VisualAge RPG

Page 111: c 0924494

Ejemplo de recuadro de listaAccione el pulsador Añadir para insertar en la lista el valor de texto delcomponente campo de entrada. Accione el pulsador Borrar para borrar la lista, elpulsador Seleccionar para seleccionar un elemento de la lista y el pulsadorEliminar para eliminar el elemento seleccionado de la lista. Pulse Cerrar parafinalizar el programa.

Capítulo 7. Utilización de componentes 93

Page 112: c 0924494

********************************************************************** ** ID de programa : LISTBOX ** ** Descripción . : Programa de ejemplo que muestra el componente ** cuadro de lista. ** ********************************************************************************************************************************************* ** Ventana. . : MAIN ** ** Componente : CLEAR ** ** Evento . . : PRESS ** ** Descripción: Borrar el recuadro de lista y el campo de entrada. ** Poner el foco en el componente campo de entrada. ** ***********************************************************************

C CLEAR BEGACT PRESS MAIN*

C 'LB1' setatr 0 'RemoveItem'C 'EF1' setatr *blanks 'Text'C 'EF1' setatr 1 'Focus'*

C ENDACT********************************************************************** ** Ventana . : FRA0000B ** ** Componente : CLOSE ** ** Evento . . : PRESS ** ** Descripción: Terminar el programa ** ***********************************************************************

C CLOSE BEGACT PRESS MAIN*

C move *on *INLR*

C ENDACT

Figura 20. Ejemplo de codificación utilizando el componente Cuadro de lista (Pieza 1 de 3)

94 Programación con VisualAge RPG

Page 113: c 0924494

********************************************************************** ** Ventana. . : MAIN ** ** Componente : REMOVE ** ** Evento . . : PRESS ** ** Descripción: Eliminar el elemento seleccionado del recuadro de ** lista. Se utiliza el atributo 'FirstSel' para ** determinar el índice del primer elemento ** seleccionado. ** ***********************************************************************

C REMOVE BEGACT PRESS MAIN*

C 'LB1' getatr 'FirstSel' Index 3 0*

C Index ifgt *zeroC 'LB1' setatr Index 'RemoveItem'C endif*

C ENDACT********************************************************************** ** Ventana . : FRA0000B ** ** Componente : ADD ** ** Evento . . : PRESS ** ** Descripción: Añade el valor del componente campo de entrada como ** nuevo elemento al componente recuadro de lista. ** ***********************************************************************

C ADD BEGACT PRESS MAIN*

C 'EF1' getatr 'TEXT' tmp 30*

C tmp ifne *blanksC 'LB1' setatr tmp 'InsertItem'C 'EF1' setatr *blanks 'Text'C 'EF1' setatr 1 'Focus'C endif*

C ENDACT

Figura 20. Ejemplo de codificación utilizando el componente Cuadro de lista (Pieza 2 de 3)

Capítulo 7. Utilización de componentes 95

Page 114: c 0924494

Ejemplo de búsquedaPuede utilizar los atributos Search, SearchType y Case para buscar un elementoconcreto de la lista. Es más rápido utilizar estos atributos que leer cada elementoen el programa y comparar para encontrar valores específicos.

El ejemplo siguiente muestra cómo localizar un nombre de cliente en un recuadrode lista escribiendo un nombre en el campo de entrada. La ventana se denominaMAIN, el recuadro de lista es LB1 y el campo de entrada es EF1. La interfaz deusuario es la siguiente:

********************************************************************** ** Ventana. . : MAIN ** ** Componente : SELECT ** ** Evento . . : PRESS ** ** Descripción: Recupera el elemento seleccionado del recuadro de ** lista y lo copia en el campo de entrada. ** ***********************************************************************

C SELECT BEGACT PRESS MAIN*

C 'LB1' getatr 'FirstSel' x 3 0*

C x ifgt *zeroC 'LB1' setatr x 'Index'C 'LB1' getatr 'GetItem' temp 20C 'EF1' setatr temp 'Text'C endif*

C ENDACT********************************************************************** ** Ventana. . : MAIN ** ** Componente : EF1 ** ** Evento . . : CHANGE ** ** Descripción: Para sucesos notify en ejemplos CRP ** ***********************************************************************

C EF1 BEGACT CHANGE MAIN*

C ENDACT*

Figura 20. Ejemplo de codificación utilizando el componente Cuadro de lista (Pieza 3 de 3)

96 Programación con VisualAge RPG

Page 115: c 0924494

En el evento Create de la ventana, el atributo Case del recuadro de lista seestablece en 0 para indicar que la búsqueda no es sensible a las mayúsculas yminúsculas. El atributo SearchType se establece en 1 para indicar que sóloqueremos comparar el número de caracteres de la serie de búsqueda con losprimeros caracteres del elemento de la lista. El resto del código consiste en rellenarel recuadro de lista con registros de la base de datos del sistema AS/400.C MAIN BEGACT CREATE MAIN*

C 'LB1' Setatr 0 'Case'C 'LB1' Setatr 1 'SearchType'*

C Read Custom01 99*

C DoW NOT *in99C 'LB1' Setatr CustNa 'AddItemEnd'C Read Custom01 99C EndDo*

C 'LB1' Setatr 1 'SelectItem'*

C ENDACT

El código siguiente es la subrutina de acciones para el evento Change del campode entrada EF1. Cada vez que se escribe un carácter en el campo de entrada, seinvoca a esta subrutina de acciones.

Se recupera el valor del atributo Text del campo de entrada y, si no está en blanco,se utiliza ese valor como la serie de búsqueda para el atributo Search del recuadrode lista. Si se encuentra una coincidencia (el atributo Index es mayor que 0), seselecciona el elemento encontrado y se mueve al principio del recuadro de lista conel atributo SetTop .C EF1 BEGACT CHANGE MAIN*

C 'EF1' Getatr 'Text' Search 40*

C If Search <> *BlanksC 'LB1' Setatr Search 'Search'*

Capítulo 7. Utilización de componentes 97

Page 116: c 0924494

C If %Getatr('Main':'LB1':'Index')<>0C Eval %Setatr('Main':'LB1':'SelectItem')=C %Getatr('Main':'LB1':'Index')C Eval %Setatr('Main':'LB1':'SetTop')=C %Getatr('Main':'LB1':'Index')C EndIf*

C ElseC 'LB1' Setatr 1 'SetTop'C 'LB1' Setatr 1 'SelectItem'C 'LB1' Setatr 1 'Index'*

C EndIf*

C ENDACT

Si el campo de entrada está en blanco, se mueve el primer elemento del recuadrode lista al principio y se selecciona. El atributo INDEX se establece en 1 para quelas búsquedas siguientes empiecen al principio de la lista.

98 Programación con VisualAge RPG

Page 117: c 0924494

Medios

Utilice el componente medios para reproducir o grabar información de audio opara reproducir archivos de vídeo.

El componente medios ofrece a los programas la posibilidad de procesar archivosde ondas (.WAV), MIDI (.MID) y QuickTime Movie (.MOV). Si desea utilizar estosarchivos de audio, el PC debe estar equipado con una tarjeta de sonido que puedaprocesar estos archivos. Para grabar un archivo de sonido, necesitará un micrófonoo algún otro dispositivo de entrada soportado por la tarjeta de sonido. Losarchivos MIDI no pueden grabarse con el componente medios.

Las aplicaciones Java deben tener instalada la API JMF (Java Media Framework).El componente medios sólo permite reproducir los archivos de audio y de vídeo enel entorno Java.

Los formatos de archivo de vídeo que se pueden procesar son: MPEG (*.mpg),QUICKTIME Movie (*.mov), *.dat y *.avi de Microsoft® Video para Windows enWindows NT/95/98. Para reproducir estos archivos de vídeo, el sistema debe tenerlos controladores adecuados.

Atributos de componente

AddLink* AllowLink* AudioMode Bass*Bottom FileName Handle* InPlaceLeft Length Panel ParentNamePartName PartType Position RemoveLink*Top Treble* UserData VisibleVolumen

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Complete Create Destroy Link*

*Nota: Consulte la descripción del evento si desea saber cuáles son lasrestricciones.

Especificación de un nombre de archivoUtilice el valor del atributo FileName para especificar el nombre del archivo quedesea procesar. Si desea más información, consulte el “Capítulo 12. Utilización dearchivos de imágenes, de sonido y de vídeo” en la página 233.

Nota: Algunos archivos de ondas se suministran en formato comprimido. Elcomponente medios sólo procesa los archivos de ondas sin comprimir.

Capítulo 7. Utilización de componentes 99

Page 118: c 0924494

Establecimiento de AudioModePara procesar un archivo, establezca el atributo AudioMode en uno de los valoressiguientes:

Valor Descripción

1 Pausa — Suspende el proceso del archivo

2 Reproducir — Reproduce el archivo

3 Grabar — Graba un archivo

4 Parar — Detiene el proceso del archivo

Establecimiento de VolumeUtilice el atributo Volume para establecer el volumen del componente medios y lasalida de ondas y el sintetizador del sistema.

Establecimiento de PositionUtilice el atributo Position para determinar la posición inicial del archivo que va aprocesarse. Exprese el valor del atributo en milisegundos.

Utilización del componente Panel de mediosPuede utilizar el componente panel de medios para controlar el componentemedios. En el cuaderno de propiedades del componente panel de medios,establezca el nombre de componente medios del atributo AddLink y habilite elatributo AllowLink. De este modo, el usuario puede controlar el componentemedios con sólo pulsar el botón adecuado en el panel de medios. Consulte elapartado “Panel de medios” en la página 101 si desea más información.

Señalización de eventosCuando un componente medios ha procesado un archivo por completo, se señalaun evento Complete.

100 Programación con VisualAge RPG

Page 119: c 0924494

Panel de medios

Nota: Este componente no se utiliza en las aplicaciones Java.

Utilice el componente panel de medios para proporcionar un acceso rápido a lasacciones más utilizadas.

También puede utilizarlo para dar al usuario control sobre otros componentes sinnecesidad de crear lógica de programa. Por ejemplo, puede utilizarlo para crearpulsadores o controles de graduador que controlen el volumen o la modalidad deun componente medios.

En el cuaderno de propiedades del componente panel de medios, puede indicar losiguiente:v Qué botones, de un grupo definido, contendrá el panel de mediosv Si los graduadores de posición y volumen se visualizarán

Nota: El componente panel de medios sólo se puede soltar en una página delcuaderno con lienzo o en una ventana con lienzo.

Atributos de componente

AddLink AllowLink BackColor BackMixBottom Enabled Handle HeightLeft PanelItem PanelMode ParentNamePartName PartType Position RemoveLinkTop UserData Visible VolumeWidth

Eventos a los que puede aplicarse

Change Create Destroy LinkMouseEnter MouseExit MouseMove PopupPress

Creación de un componente panel de mediosUn componente panel de medios sólo puede crearse en un componente lienzo.

Enlace con otros componentesHay dos métodos de enlazar un componente panel de medios con otrocomponente: uno es mediante el cuaderno de propiedades, mientras que con elotro se ha de escribir la lógica del programa. El primer método es el más sencillo.El único caso en que tiene que escribir la lógica del programa es si desea que seestablezca el enlace durante el tiempo de ejecución y luego establecerá los atributosAddLink y AllowLink. Un ejemplo típico sería enlazar el panel de medios con uncomponente medios. Cuando se cambia un control en el panel de medios, elmecanismo de enlace afecta automáticamente al componente medios.

Capítulo 7. Utilización de componentes 101

Page 120: c 0924494

Cuando se crea un enlace desde el componente panel de medios con otrocomponente, sólo ciertos botones se habilitan en el componente panel de medios.Para habilitar todos los botones, también debe crear un enlace desde el otrocomponente hasta el componente panel de medios.

Consulte la descripción de AddLink de la publicación VisualAge RPG Manual deconsulta de componentes, SC10-3065-02 (SC09-2450-02) para obtener más informaciónsobre los componentes que puede enlazar con un componente panel de medios.

Señalización de eventosCuando se mueve el graduador de volumen o el graduador de posición, se señalaun evento Change. Utilice el atributo PanelItem para determinar el graduador quese cambió. Utilice el atributo Volume para determinar el valor del graduador devolumen y el atributo Position para determinar el valor del graduador de posición.

Cuando se acciona un pulsador en el panel de medios, se señala un evento Press.Utilice el valor numérico devuelto por el atributo PanelItem para determinar québotón causó el evento Press. Consulte la publicación VisualAge RPG Manual deconsulta de componentes, SC10-3065-02 (SC09-2450-02) para ver la lista de los valoresposibles.

102 Programación con VisualAge RPG

Page 121: c 0924494

Barra de menús

Utilice el componente barra de menús para proporcionar a los usuarios acceso alos menús desplegables. Puede añadir componentes submenú y opción de menú ala barra de menús.

Las barras de menús aparecen en la parte superior del marco de la ventana, debajode la barra de título. Cuando el usuario selecciona un menú en ella, aparece unmenú desplegable con todas sus opciones. Al seleccionar una de ellas se iniciainmediatamente la acción que describe.

Nota: Las propiedades, los eventos y otros elementos de este componente sólo sepueden manipular desde su menú emergente de la vista de árbol deproyectos.

Para obtener información relacionada, consulte el apartado:v “Elemento de menú” en la página 104v “Submenú” en la página 166v “Menú emergente” en la página 132

Atributos de componente

PartType PartName ParentName UserData

Eventos a los que puede aplicarse

Create Destroy

Creación de menús desplegablesNo se puede abrir el cuaderno de propiedades de una barra de menús, submenú uopción de menú pulsando dos veces con el ratón en ellos ni a través de menúsemergentes. Debe hacerlo en la vista de árbol.

Capítulo 7. Utilización de componentes 103

Page 122: c 0924494

Elemento de menú

Utilice las opciones de menú para crear menús desplegables o emergentes.

Una opción de menú describe una acción que se inicia cuando el usuarioselecciona esa opción.

Para crear un menú:1. Suelte un componente submenú en una barra de menús o en un menú

emergente.2. Suelte opciones de menú en el submenú.

Nota: Las propiedades, los eventos y otros elementos de este componente sólo sepueden manipular desde su menú emergente de la vista de árbol deproyectos.

Para obtener información relacionada, consulte el apartado:v “Barra de menús” en la página 103v “Menú emergente” en la página 132v “Submenú” en la página 166

Atributos de componente

Checked Enabled FileName LabelParentName PartName PartType UserData

Eventos a los que puede aplicarse

Create Destroy MenuSelect

Colocación de una marca de selección junto a una opción demenú

Un símbolo de marca de selección junto a una opción de menú informa al usuarioque la acción representada por la opción de menú está seleccionada. Por ejemplo,si aparece una marca de selección junto al elemento de menú Mostrar cuadrícula,se visualizará una cuadrícula.

Para visualizar una marca de selección junto a un elemento de menú, establezca elatributo Checked en 1. Para eliminar la marca de selección, establezca el atributoen 0.

Establecimiento del texto de menúUtilice el atributo Label para establecer el texto para un elemento de menú.

Establecimiento de un nemotécnico

Nota: Las aplicaciones Java no soportan nemotécnicos.

104 Programación con VisualAge RPG

Page 123: c 0924494

Para especificar una clave nemotécnica para el elemento de menú, coloque elidentificador nemotécnico delante de un carácter en el texto del atributo Label. EnWindows NT/95/98, se utiliza el símbolo &. El carácter al que se ha asignado laclave nemotécnica se visualiza en la interfaz con un subrayado, por ejemplo,Visualizar. El subrayado informa a los usuarios que pueden seleccionar elelemento de menú pulsando la tecla del carácter subrayado en el teclado.

Habilitación de elementos de menúPuede controlar si se emite un evento MenuSelect o no, cuando un usuarioselecciona un elemento de menú.

Por omisión, el elemento de menú queda habilitado al crearlo. Un elemento demenú habilitado genera un evento MenuSelect cuando se selecciona.

Establezca el atributo Enabled en 0 si no desea tener habilitado un elemento demenú. Cuando no está habilitado, el elemento de menú aparece en una tonalidadatenuada en la pantalla y no genera un evento MenuSelect al seleccionarse.

Señalización de eventosCuando el usuario selecciona un elemento de menú, se señala un eventoMenuSelect.

Nota: Sólo los elementos de menú señalan un evento MenuSelect. Los submenús(como los menús en cascada), que están asociados a otros menús no loseñalan.

Capítulo 7. Utilización de componentes 105

Page 124: c 0924494

Subarchivo de mensajes

Utilice el componente subarchivo de mensajes para visualizar mensajespredefinidos o para visualizar texto proporcionado en la lógica del programa: porejemplo, información de error o de estado.

Este componente está situado siempre en la parte inferior de la ventana y ocupa laanchura de la ventana. No se puede cambiar la anchura de este componente; sinembargo, sí se puede cambiar la altura para que se visualicen más mensajes. Entiempo de ejecución, los usuarios pueden utilizar las barras de desplazamientopara ver todos los mensajes.

Atributos de componente

AddMsgID AddMsgText Count DragEnable*DropEnable* Enabled FirstSel FontBoldFontItalic FontName FontSize FontStrike*FontUnder* ForeColor ForeMix GetItemHandle* Height Index MsgSubTextNbrOfSel ParentName PartName PartTypeRemoveMsg Selected ShowTips TipTextUserData Visible

* Nota:: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy Drop EnterMouseEnter MouseExit MouseMove PopupSelect

Visualización de mensajes predefinidosPara visualizar mensajes que ya están definidos en el Diseñador GUI, establezca elatributo AddMsgId en el número de ID del mensaje que desee visualizar. Utilice laparte numérica del identificador de mensaje.

Visualización de texto suministrado en el programaPara visualizar texto que no forme parte de un mensaje predefinido, utilice elatributo AddMsgText en el programa y suministre una serie de texto o un literalcomo valor del mensaje.

Utilización de variables de sustituciónEl componente subarchivo de mensajes soporta variables de sustitución. Unavariable de sustitución se define cuando se crea el mensaje escribiendo el carácterde porcentaje ( % ) seguido de un valor numérico (por ejemplo, %123). Estavariable de sustitución se sustituye con datos que proporciona el programa antes

106 Programación con VisualAge RPG

Page 125: c 0924494

de que el usuario añada el mensaje. Los datos de sustitución del mensaje seaplican a los atributos AddMsgID y AddMsgText.

Los datos de sustitución de mensaje son una serie de palabras separadas porblancos. Cada palabra de sustitución sustituye a la variable de sustitucióncorrespondiente antes de que se añada el mensaje al componente subarchivo demensajes. Para establecer los datos de sustitución del mensaje, utilice el atributoMsgSubText antes de establecer el atributo AddMsgID.

Nota: Los datos de sustitución siguen vigentes hasta que se utiliza otro atributoMsgSubText.

Eliminación de mensajesUtilice el atributo RemoveMsg para eliminar un mensaje del componentesubarchivo de mensajes. Especifique el número de índice del mensaje que se va aeliminar. Para eliminar todos los mensajes, utilice un valor de índice 0.

Capítulo 7. Utilización de componentes 107

Page 126: c 0924494

Ejemplo de subarchivo de mensajesEn este ejemplo se solicita al usuario que entre un número de componente paraprocesar. El número de componente debe ser mayor que cero y menor que 2000.Cuando se accione el pulsador Aceptar, el programa comprobará si el valor está enel rango necesario. Si el valor no está dentro del rango, se añade un mensaje alcomponente subarchivo de mensajes.

********************************************************************** ** ID de programa : MESSAGE ** ** Descripción . : Programa de ejemplo que muestra el componente ** subarchivo de mensajes. ** ********************************************************************************************************************************************* ** Ventana. . : MAIN ** ** Componente : PB_CLOSE ** ** Evento . . : PRESS ** ** Descripción: Terminar el programa ** ***********************************************************************

C PB_CLOSE BEGACT PRESS MAIN*

C move *on *inlr*

C ENDACT

Figura 21. Ejemplo de código en el que se utiliza el componente subarchivo de mensajes(Pieza 1 de 2)

108 Programación con VisualAge RPG

Page 127: c 0924494

********************************************************************** ** Ventana. . : MAIN ** ** Componente : PB_OK ** ** Evento . . : PRESS ** ** Descripción: Comprobar que el valor entrado está permitido. De lo ** contrario, añada un mensaje al componente subarchivo ** de mensajes. ** ** Se utiliza el valor entrado como texto de ** sustitución en el mensaje. ** ***********************************************************************

C PB_OK BEGACT PRESS MAIN** Borrar el subarchivo de mensajes*

C 'Msg1' setatr 0 'RemoveMsg'** Obtener el número de componente*

C 'PartNum' getatr 'Text' tmp4 4 0 ** Si el número de componente no es válido, añada un mensaje* al componente mensaje. El número de componente entrado por* el usuario se utiliza como texto de sustitución.* Dado que el texto de sustitución debe ser una serie, mueva* el valor numérico de número de componente a un campo de* caracteres y utilícelo como texto de sustitución.

C tmp4 ifle *zeroC tmp4 orgt 1999C move tmp4 char4 4C 'Msg1' setatr char4 'MsgSubText'C 'Msg1' setatr 1 'AddMsgID'** Dar FOCO al campo de entrada PartNum para que el cursor* regrese al mismo.

C 'PartNum' setatr 1 'Focus'** El número de componente está bien, seguir procesando

C else* ...* ...* ...

Figura 21. Ejemplo de código en el que se utiliza el componente subarchivo de mensajes(Pieza 2 de 2)

Capítulo 7. Utilización de componentes 109

Page 128: c 0924494

Edición de múltiples líneas

Utilice el componente edición de múltiples líneas si desea que el usuario puedaescribir varias líneas de texto.

El componente edición de múltiples líneas tiene límites definidos. A veces no sevisualiza todo el texto que contiene. El usuario puede desplazar el texto vertical yhorizontalmente para ver la parte que no se visualiza.

Atributos de componente

AddLineEnd AddOffset BackColor BackMixBottom CanUndo CharOffset CopyCsrLine CsrPos Cut DeleteDragEnable* DropEnable* Enabled FocusFontBold FontItalic FontName FontSizeFontStrike* FontUnder* ForeColor ForeMixHandle* Height InsertLine InsertTextLeft LineNumber LineText NbrOfLinesParentName PartName PartType PasteReadOnly Refresh ShowTips TextTextEnd TextLength TextSelect TextStartTextString TipText Top TopLineUndo UserData Visible WidthWordWrap

* Nota:: Consulte la descripción del atributo para conocer las restricciones.

Eventos a los que puede aplicarse

Change Click Create DblClickDestroy Drop GotFocus KeyPressLostFocus MouseDown MouseEnter MouseExitMouseMove MouseUp Popup VKeyPress

Obtención y establecimiento del textoUtilice el atributo Text para obtener o establecer el texto del componente ediciónde múltiples líneas.

Nota: El texto por omisión entrado en el cuaderno de propiedades para elcomponente edición de múltiples líneas no se guarda. El texto para uncomponente edición de múltiples líneas sólo puede establecerse en el tiempode ejecución.

Manipulación de líneas de texto en un componente de ediciónde múltiples líneas

Para insertar líneas nuevas en un componente edición de múltiples líneas:

110 Programación con VisualAge RPG

Page 129: c 0924494

1. Establezca el atributo LineNumber en el número de línea después del cualdesea insertar texto.

2. Utilice el atributo InsertLine.El texto se inserta después de la línea que se especifica. Cualquier línea queesté por debajo de la línea que ha especificado se desplazará hacia abajo paradejar espacio para el texto insertado.

Manipulación de caracteres en un componente de edición demúltiples líneas

Para insertar una serie de caracteres en un componente edición de múltiples líneas:1. Establezca el atributo CharOffset para especificar dónde desea que se inserte el

texto nuevo.El texto que sigue al valor CharOffset se sustituye por el texto nuevo.

2. Utilice el atributo AddOffset para añadir texto en CharOffset.

Manipulación de partes seleccionadas del texto en uncomponente edición de múltiples líneas

Puede utilizar varios atributos para manipular partes seleccionadas del texto en uncomponente edición de múltiples líneas.

Para devolver sólo el texto seleccionado, utilice el atributo TextSelect. Si no seselecciona texto, el atributo TextSelect devuelve una serie nula y el campo deresultado que debe recibir el texto permanece invariable.

Utilice los atributos TextStart y TextEnd para devolver las posiciones de caracteresinicial y final del texto seleccionado.

Cambio de colorSi existe un componente edición de múltiples líneas en un componente lienzo conel color de fondo establecido en el valor por omisión del sistema, cambia al colorde fondo del lienzo que el componente edición de múltiples líneas heredará. Loscomponentes edición de múltiples líneas adicionales añadidos al lienzo noheredarán el color de fondo del lienzo. Para corregirlo, difiera el establecimientodel color de fondo del lienzo hasta que haya colocado todos los componentesedición de múltiples líneas en el lienzo. Como alternativa, puede hacer que loscomponentes edición de múltiples líneas hereden el color estableciendo el color dellienzo en el valor por omisión del sistema, y luego otra vez en el valor del colorRGB predefinido.

Si arrastra y suelta un color en la barra de desplazamiento de un componenteedición de múltiples líneas, ese color no se guardará. El componente edición demúltiples líneas cambiará al nuevo color, pero cuando se cierre la ventana y vuelvaa abrirse, el color volverá a ser el original.

Elección de fontsNo todos los fonts están soportados por el componente edición de múltiples líneas.Después de seleccionar un font para este componente, se ajustará para visualizar lacoincidencia más próxima para el font seleccionado.

Cómo evitar la entrada de datos por parte del usuarioPuede evitar que el usuario entre texto en el componente edición de múltipleslíneas, realizando una de las acciones siguientes:

Capítulo 7. Utilización de componentes 111

Page 130: c 0924494

v Establezca el atributo ReadOnly en 0.v Establezca el atributo Enabled en 0. (Esto también impide que el componente

edición de múltiples líneas responda a eventos tales como Change y GotFocus.)

Sigue siendo posible cambiar el valor del componente edición de múltiples líneasen el programa.

Ejemplo de edición de múltiples líneasEn este ejemplo, al accionar el pulsador Copiar se copia el texto seleccionadodesde la edición de múltiples líneas hasta el campo de entrada. Al accionar elpulsador Cerrar finaliza el programa.

112 Programación con VisualAge RPG

Page 131: c 0924494

********************************************************************** ** ID de programa : MLE ** ** Descripción . : Programa de ejemplo que muestra el componente ** edición de múltiples líneas. ** ******************************************************************************************************************************************** ** Ventana. . : MAIN ** ** Componente : PB_CLOSE ** ** Evento . . : PRESS ** ** Descripción: Terminar el programa ** ***********************************************************************

C PB_CLOSE BEGACT PRESS MAIN*

C move *on *inlr*

C ENDACT********************************************************************** ** Ventana. . : MAIN ** ** Componente : PB_COPY ** ** Evento . . : PRESS ** ** Descripción: Copiar el texto seleccionado en el MLE al componente ** edición de múltiples líneas. ** ***********************************************************************

C PB_COPY BEGACT PRESS MAIN*

C 'EF1' setatr *blanks 'Text'C 'MLE1' getatr 'TextStart' start 5 0C 'MLE1' getatr 'TextSelect' selected 128*

C start ifgt *zeroC 'ef1' setatr selected 'Text'C endif*

C ENDACT

Figura 22. Ejemplo de código en el que se utiliza el componente edición de múltiples líneas(Pieza 1 de 2)

Capítulo 7. Utilización de componentes 113

Page 132: c 0924494

********************************************************************** ** Ventana . : Main ** ** Componente : Top ** ** Evento . . : Press ** ** Descripción: Establecer la 5ª línea del componente edición de ** múltiples líneas como línea superior ** ** Cambios . : ** ***********************************************************************

C TOP BEGACT PRESS MAIN*

C eval %setatr('MAIN':'MLE1':'TOPLINE') = 5C ENDACT********************************************************************** ** Ventana . : Main ** ** Componente : Bottom ** ** Evento . . : Press ** ** Descripción: Establecer la parte inferior ** ***********************************************************************

C BOTTOM BEGACT PRESS MAIN*

C eval %setatr('MAIN':'MLE1':'TOPLINE') = 0C ENDACT

Figura 22. Ejemplo de código en el que se utiliza el componente edición de múltiples líneas(Pieza 2 de 2)

114 Programación con VisualAge RPG

Page 133: c 0924494

Cuaderno

Utilice el componente cuaderno para presentar datos que se pueden agruparlógicamente por temas: por ejemplo, información de cliente dividida en categoríastales como Nombre, Dirección de envío, Pedidos y Créditos.

Un componente cuaderno es una representación gráfica en forma de cuaderno. (Enaplicaciones Windows, recibe el nombre de control de separadores). Puede añadirpáginas al cuaderno y agruparlas en secciones separadas por separadores. Si lapágina de cuaderno tiene lienzo, puede añadir más de un componente a la misma.Si no tiene lienzo, sólo se puede añadir un componente.

El usuario puede pasar las páginas de un cuaderno para ir de una página a otra oir directamente a una sección del cuaderno pulsando el botón del ratón sobre lapestaña.

Puede añadir páginas de cuaderno del modo siguiente:v Utilizando el cuaderno de propiedades del componente cuadernov Señalando y pulsando (o arrastrando y soltando) una página de cuaderno o una

página de cuaderno con lienzo en el componente cuaderno.

Para obtener información relacionada, consulte el apartado:v “Página de cuaderno” en la página 116v “Página de cuaderno con lienzo” en la página 117

Atributos de componente

BackColor BackMix Bottom CountEnabled Focus FontBold FontItalicFontName FontSize FontStrike* FontUnder*ForeColor ForeMix Handle* HeightLeft PageNumber ParentName PartNamePartType Refresh ShowTabs* TopUserData Visible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy

Cambio del énfasis del fontAl cambiar el énfasis del font para un componente cuaderno a subrayado otachadura, el texto de estado adopta el nuevo énfasis, pero no así el texto de losseparadores.

Capítulo 7. Utilización de componentes 115

Page 134: c 0924494

Página de cuaderno

Utilice el componente página de cuaderno para añadir páginas a un cuaderno.

Solamente puede añadir un componente a una página de cuaderno; el tamaño delmismo se adaptará a la página. Si desea añadir más de un componente en unapágina, debe colocar un componente lienzo en la página de cuaderno. Tambiénpuede utilizar el componente página de cuaderno con lienzo para ahorrarse unpaso.

Nota: Las propiedades, los eventos y otros elementos de este componente sólo sepueden manipular desde su menú emergente de la vista de árbol deproyectos.

El usuario puede pulsar las teclas de flecha izquierda y derecha para ir de unapágina a otra.

Para obtener información relacionada, consulte el apartadov “Cuaderno” en la página 115v “Página de cuaderno con lienzo” en la página 117

Atributos de componente

Enabled ParentName PartName PartTypeRefresh TabImage TabLabel UserDataVisible

Eventos a los que puede aplicarse

Create Destroy PageSelect

Mostrar el texto del separadorEn una máquina DBCS, puede que el separador de un cuaderno no muestre todoel texto cuando se utiliza el font MINCHO Proportional. Esto se solucionacambiando el font por otro estilo, como MINCHO Normal o MINCHO System.

Establecimiento de un nemotécnicoPara especificar una clave nemotécnica para el elemento de menú, coloque elidentificador nemotécnico delante de un carácter en el texto del atributo Label. Elcarácter al que se ha asignado la clave nemotécnica se visualiza en la interfaz conun subrayado (por ejemplo, Visualizar). Tenga en cuenta que para WindowsNT/95/98, las claves nemotécnicas se visualizan, pero no funcionan en páginas delcuaderno.

Nota: Las aplicaciones Java no soportan nemotécnicos

116 Programación con VisualAge RPG

Page 135: c 0924494

Página de cuaderno con lienzo

Utilice la página de cuaderno con lienzo para añadir páginas a un componentecuaderno.

El componente lienzo ocupa el área de cliente de un componente página decuaderno. Si se añaden componentes al lienzo se puede crear una interfaz gráficade usuario.

Si sólo desea añadir un componente a la página, puede utilizar el componentepágina de cuaderno en lugar del componente página de cuaderno con lienzo.Puesto que dicho componente no tiene lienzo, el tamaño del componente que seañada se ajustará automáticamente.

Para obtener información relacionada, consulte el apartado:v “Página de cuaderno” en la página 116v “Cuaderno” en la página 115

Atributos de componente

Enabled ParentName PartName PartTypeTabImage TabLabel UserData Visible

Eventos a los que puede aplicarse

Create Destroy PageSelect

Capítulo 7. Utilización de componentes 117

Page 136: c 0924494

Interfaz ODBC/JDBC

El componente Interfaz ODBC/JDBC proporciona la posibilidad de procesararchivos de base de datos que den soporte a la API ODBC de Windows o la APIJDBC de JavaSoft. Foxpro, Access y Paradox son ejemplos de estos tipos dearchivos de base de datos.

Para desarrollar aplicaciones que puedan utilizar el componente InterfazODBC/JDBC, debe estar familiarizado con SQL y tener instalado el SDK ODBC deWindows o el Java 2 Software Development Kit (J2SDK), Standard Edition, deJavaSoft en la estación de trabajo.

Si no tiene el SDK ODBC, puede bajarlo de Microsoft en el URL siguiente:http://www.microsoft.com/odbc/download.htm

El soporte de JDBC forma parte del Java™ 2 Software Development Kit (J2SDK)Versión 1.2 para Windows. Si no tiene el J2SDK, puede bajarlo de SunMicrosystems en el URL siguiente:http://www.javasoft.com/products/

Las aplicaciones que acceden y manipulan datos de una base de datos JDBCnecesitan el controlador de conformidad con JDBC 2.0 adecuado. Puede encontrarel controlador JDBC y más información en el URL siguiente:http://java.sun.com/products/jdbc/

Nota: JDBC no se puede utilizar en applets.

Una base de datos ODBC o JDBC se compone de una o varias tablas. Los datos sealmacenan en una tabla como una serie de filas. Cada fila, o registro, contiene unnúmero de columnas con datos. El programa puede someter sentencias SQL juntocon los atributos del componente Interfaz ODBC/JDBC para manipular filas, opara traspasar datos entre campos del programa y columnas de tablas.

Para poder procesar una base de datos existente, el programa VARPG debeconectarse antes a la base de datos e indicar a qué tabla hace referencia. Paramanipular las filas de una tabla, el programa debe crear un conjunto de registrosque identifique los registros que el componente interfaz ODBC/JDBC debedevolver y mantener. Para acceder a los datos de una fila, debe enlazar cada unade las columnas utilizadas en la fila de la tabla con un campo del programa. En lasaplicaciones Java no se pueden utilizar los punteros. Una columna está enlazada aun componente; para enlazar sólo se pueden utilizar los componentes texto estáticoy campo de entrada.

Si crea una aplicación Java que utiliza el componente Interfaz ODBC/JDBC, losusuarios finales que ejecuten la aplicación deben instalar el archivo varpgjdb.jar ensus estaciones de trabajo y añadir su ubicación en la sentencia classpath. Elprograma de utilidad de empaquetamiento no incluye este archivo JAR. El archivoJAR está ubicado en el subdirectorio adtswin\java.

118 Programación con VisualAge RPG

Page 137: c 0924494

Atributos de componente

AllowChg* BindPart Bottom BufferDec*BufferLen* BufferPtr* BufferType* CharDataColumn ColumnDec ColumnLen ColumnNameColumnas ColumnType Connect ConnectedConnectStr CurrentRow DeleteRow ExecuteSQLFetch FetchNext FetchPrior GetTablesHandle* Height InsertRow IsDataLeft ParentName PartName PartTypeRefresh Rows* SQLError SQLMsgBoxSQLQuery Top UnBind UpdateRowUserData Visible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy

Conexión a una base de datos ODBCPara poder procesar una base de datos existente, el programa VARPG debeconectarse antes a la base de datos e indicar a qué tabla hace referencia.

Nota: El componente Interfaz ODBC/JDBC de VARPG sólo se puede conectar a lastablas de una en una. Si esa tabla tiene dependencias o relaciones con otrastablas, el programa no podrá actualizar ni suprimir registros de la base dedatos.

Para conectarse a una base de datos, antes debe establecer el atributo ConnectStren la serie de conexión necesaria para la base de datos. Después, utilice el atributoConnect para efectuar la conexión. En Windows, si establece el atributo ConnectStren *BLANKS, el gestor ODBC visualizará el diálogo Seleccionar fuente de datosdonde podrá seleccionar la tabla a la que conectarse. Una vez realizada laconexión, el atributo Connected se establecerá en 1. Si la conexión no se consiguerealizar, el atributo Connected se establece en 0.

Al ejecutarse el fragmento de código siguiente, se visualizará el diálogo Seleccionarfuente de datos. Si se ha seleccionado una tabla, el atributo ConnectStr contendrála serie de conexión. El atributo Connect se establece para efectuar la conexión.C 'ODBC' Setatr *Blanks 'ConnectStr'C 'ODBC' Setatr 1 'Connect'C If %Getatr('Main':'ODBC':'Connected')=1C ...C ElseC ...C EndIf

Creación de un conjunto de registrosUna vez conectado a una base de datos, debe crear un conjunto de registros parapoder acceder a los datos de la base de datos. Para crear un conjunto de registros,debe someter una sentencia SELECT para el componente Interfaz ODBC/JDBC

Capítulo 7. Utilización de componentes 119

Page 138: c 0924494

utilizando los atributos SQLQuery y ExecuteSQL. La sentencia SELECT identificacuál es la tabla de la base de datos a la que se accede y cuál es el grupo deregistros de la tabla que se va a procesar.

El segmento de código siguiente es un ejemplo de creación de un conjunto detodos los registros de la tabla CUSTOMERS:D SelAll C 'Select * From "Customers"'*

C 'ODBC' Setatr SelAll 'SQLQuery'C 'ODBC' Setatr 1 'ExecuteSQL'

Acceso a los datos de una tablaLos datos se almacenan en una tabla como una serie de filas. Cada fila contiene unnúmero de columnas con datos. Las filas de una tabla se pueden manipular conatributos del componente Interfaz ODBC/JDBC como, por ejemplo, FetchNext,FetchPrior, UpdateRow, etc. Sin embargo, para acceder a los datos de una fila, debeenlazar cada una de las columnas de la fila de la tabla con un campo delprograma. Una vez establecido este enlace, el componente Interfaz ODBC/JDBCpuede traspasar datos entre los campos del programa y las columnas de la tabla.

Para enlazar el campo del programa, debe utilizar los atributos del componenteInterfaz ODBC/JDBC siguientes:

ColumnEstablece cuál es la columna de la tabla que se enlazará.

BufferPtrContiene la dirección del campo del programa que se enlaza a la columna.

BufferDecEspecifica el número de posiciones decimales de la columna dealmacenamiento intermedio.

BufferLenEspecifica la longitud del campo del programa.

BufferTypeIndica el tipo de datos del campo del programa.

En el ejemplo siguiente, se enlazan 2 campos definidos en las especificaciones D alas columnas 1 y 2 de una tabla:D first S 20D last S 30*

D fptr S * INZ(%Addr(first))D lptr S * INZ(%Addr(last))*

C 'ODBC1' Setatr 1 'Column'C 'ODBC1' Setatr 20 'BufferLen'C 'ODBC1' Setatr fptr 'BufferPtr'C 'ODBC1' Setatr 1 'BufferType'*

C 'ODBC1' Setatr 2 'Column'C 'ODBC1' Setatr 30 'BufferLen'C 'ODBC1' Setatr lptr 'BufferPtr'C 'ODBC1' Setatr 1 'BufferType'

También puede utilizar el %ADDR incorporado directamente en lasespecificaciones C para evitar codificar las especificaciones D para definir lospunteros:

120 Programación con VisualAge RPG

Page 139: c 0924494

C Eval %Setatr(′Main':'ODBC1':'BufferPtr')=%Addr(first)

Tipos de datosUtilice el atributo BufferType para indicar el tipo de datos del campo de programaal que hace referencia el atributo BufferPtr. El componente Interfaz ODBC/JDBCutiliza el atributo BufferType para realizar la conversión de datos correcta altraspasar datos entre el campo del programa y la columna de la tabla. Esimportante establecer correctamente este atributo, ya que no se comprueba si lostipos de campo son adecuados.

Establezca el atributo Column antes de utilizar el atributo BufferType. Si el campode programa está asociado a un componente de la interfaz, el atributo DataType sepuede utilizar para obtener el tipo de almacenamiento intermedio.

Utilice el siguiente diagrama para establecer el tipo de datos VARPG en elcorrespondiente tipo de datos SQL soportado. Especifique los atributos BufferLen yBufferDec sólo como se listan en el diagrama.

Para los tipos de datos carácter, entero o entero pequeño, especifique sólo elatributo BufferLen.

Tenga en cuenta que los tipos de datos doble, flotante y real pueden definirse enVARPG, como flotante (F) o decimal con zona. Si los define como decimal conzona, el tiempo de ejecución de VARPG sólo utilizará el número de posicionesdecimales que especifica el atributo BufferDec cuando traslade datos de lacolumna. Esto puede provocar una pérdida de precisión si el origen de datos tienemás posiciones decimales que las especificadas por el atributo BufferDec. Si defineestos campos como flotantes (F), NO especifique los atributos BufferLen niBufferDec.

Tipo de datos SQL Tipo de datosVARPG

Especifica la longituddel campo de

programa (utiliceBufferLen)

Especifica las posicionesdecimales de la columna

del almacenamientointermedio (utilice

BufferDec)Carácter CHAR XDecimal Decimal con zona XEntero Decimal con zona X

Entero pequeño Decimal con zona XDoble 8FDoble Decimal con zona X X

Coma flotante 4FComa flotante Decimal con zona X X

Real 4FReal Decimal con zona X X

Si una columna contiene un tipo de datos que el componente Interfaz ODBC/JDBCno soporta, establezca el atributo AllowChg en 0 para esa columna. El componenteInterfaz ODBC/JDBC no traspasará datos entre ningún campo de programa y lacolumna. No se efectuará ningún cambio en los datos.

Recuperación de las filas de una tablaPara procesar las filas de una tabla, antes debe crear un conjunto de registros. Unconjunto de registros es un grupo de registros que devuelve y mantiene elcomponente Interfaz ODBC/JDBC. El programa somete una sentencia SELECT

Capítulo 7. Utilización de componentes 121

Page 140: c 0924494

para el componente Interfaz ODBC/JDBC utilizando los atributos SQLQuery yExecuteSQL. Primero, el atributo SQLQuery se establece en la sentencia SQL que seejecutará. Después, el atributo ExecuteSQL se establece en 1 para ejecutar laconsulta.

En el ejemplo siguiente, todos los registros se seleccionan de la tabla Customers:D SelAll C 'Select * From "Customers"'*

C 'ODBC1' Setatr SelAll 'SQLQuery'C 'ODBC1' Setatr 1 'ExecuteSQL'

Para determinar el número de filas que se han devuelto como resultado de unatributo SQLQuery, puede comprobar el valor del atributo Rows.

Una vez devuelto el conjunto de registros, se puede procesar cada una de las filasutilizando los atributos FetchNext y FetchPrior. Establezca el atributo FetchNext en1 para devolver la fila siguiente del conjunto de registros. Establezca el atributoFetchPrior en 1 para devolver la fila anterior del conjunto de registros. Paradeterminar si un atributo FetchNext o FetchPrior ha devuelto correctamente unafila, compruebe el valor del atributo IsData. El valor 1 indica que se han devueltodatos. De lo contrario, el valor de IsData se establece en 0.

En el ejemplo siguiente, se leen todos los registros de un conjunto de registros y seañade el valor de la columna 1 (primer campo) al recuadro de lista LB1.C 'ODBC1' Setatr 1 'FetchNext'C 'ODBC1' Getatr 'IsData' Temp 1 0*

C DoW Temp = 1C 'LB1' Setatr first 'AddItemEnd'C 'ODBC1' Getatr 'IsData' TempC EndDo

Actualización de los datos de una filaPara actualizar los datos de una fila, utilice el atributo UpdateRow para especificarla fila que debe actualizarse. Tenga en cuenta que el atributo UpdateRowactualizará todas las filas. No es necesario buscar antes la fila. Sin embargo, lonormal es actualizar una fila que se acaba de buscar. En este caso, se utilizará elatributo CurrentRow. Este atributo contiene el número de la fila que se acaba debuscar.

En el segmento de código siguiente, se supone que se ha leído una fila y que se havisualizado la información en una ventana. El usuario pulsa el botón Actualizardespués de efectuar los cambios.C PB_Update BEGACT PRESS Main*

C Read 'Main'C 'ODBC1' Getatr 'CurrentRow' Row 1 0C 'ODBC1' Setatr Row 'UpdateRow'*

C ENDACT

Supresión de una filaLos pasos para suprimir una fila son semejantes a los pasos para actualizarla.(Consulte “Actualización de los datos de una fila”.) Utilice el atributo DeleteRowpara especificar la fila que se va a suprimir. Al igual que con el atributoUpdateRow, DeleteRow suprimirá todas las filas del conjunto. No es necesariobuscar antes la fila.

122 Programación con VisualAge RPG

Page 141: c 0924494

En el ejemplo siguiente, el usuario ha pulsado Suprimir para suprimir un registroque se acaba de buscar y que aparece visualizado en una ventana.C PB_Delete BEGACT PRESS Main*

C 'ODBC1' Getatr 'CurrentRow' Row 1 0C 'ODBC1' Setatr Row 'DeleteRow'*

C ENDACT

Ejemplo de componente Interfaz ODBC/JDBCEn el ejemplo siguiente se utiliza una base de datos creada con Microsoft Access.La base de datos tiene una tabla denominada CUSTOMERS. Este programa deconsulta simple visualiza una ventana que contiene los detalles de un cliente. Seproporcionan pulsadores que permiten ir a los registros siguiente y anterior, yactualizar y suprimir el registro actual.

La figura siguiente muestra la ventana de consulta:

El código de este ejemplo es el siguiente:

Capítulo 7. Utilización de componentes 123

Page 142: c 0924494

*D ConnectStr C 'DSN=MS Access 97 Database;DBQ=D:\da-D ta\help\odbc\CelDial.mdb;DefaultDir-D =D:\data\help\odbc;DriverId=25;FIL=-D MS Access;MaxBufferSiz'* Variables de trabajo

DRow S 6 0** Definir punteros a almacenamientos intermedios de campos*

DP_001 S * NúmeroDP_002 S * NombreDP_003 S * Número rep.DP_004 S * ContactoDP_005 S * Teléfono

DP_006 S * FaxDP_007 S * DirecciónDP_008 S * CiudadDP_009 S * PaísDP_010 S * Código postalDP_011 S * Localidad postal

** Seleccionar todos los registros*

DSelAll C 'Select * From "Customers"'*

Figura 23. Código para el ejemplo de consulta ODBC/JDBC (Pieza 1 de 7)

124 Programación con VisualAge RPG

Page 143: c 0924494

********************************************************************** ** Ventana . : Main ** ** Componente : Main ** ** Evento . . : Create ** ** Descripción: Enlazar campos de programa a columnas y conectar con ** tabla de base de datos CUSTOMERS ** ***********************************************************************

C Main BEGACT CREATE Main** Enlazar campos a columnas* Enlazar columna: Número*

C 'ODBC' SetAtr 1 'Column'C 'ODBC' SetAtr 7 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_001=%Addr(Number)C 'ODBC' SetAtr P_001 'BufferPtr'** Enlazar columna: Nombre*

C 'ODBC' SetAtr 2 'Column'C 'ODBC' SetAtr 40 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_002=%Addr(Name)C 'ODBC' SetAtr P_002 'BufferPtr'** Enlazar columna: Número rep.*

C 'ODBC' SetAtr 3 'Column'C 'ODBC' SetAtr 5 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_003=%Addr(Rep_number)C 'ODBC' SetAtr P_003 'BufferPtr'** Enlazar columna: Contacto*

C 'ODBC' SetAtr 4 'Column'C 'ODBC' SetAtr 30 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_004=%Addr(Contact)C 'ODBC' SetAtr P_004 'BufferPtr'*

Figura 23. Código para el ejemplo de consulta ODBC/JDBC (Pieza 2 de 7)

Capítulo 7. Utilización de componentes 125

Page 144: c 0924494

** Enlazar columna: Teléfono*

C 'ODBC' SetAtr 5 'Column'C 'ODBC' SetAtr 17 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_005=%Addr(Phone)C 'ODBC' SetAtr P_005 'BufferPtr'** Enlazar columna: Fax*

C 'ODBC' SetAtr 6 'Column'C 'ODBC' SetAtr 17 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_006=%Addr(Fax)C 'ODBC' SetAtr P_006 'BufferPtr'** Enlazar columna: Dirección*

C 'ODBC' SetAtr 7 'Column'C 'ODBC' SetAtr 40 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_007=%Addr(Address)C 'ODBC' SetAtr P_007 'BufferPtr'** Enlazar columna: Ciudad*

C 'ODBC' SetAtr 8 'Column'C 'ODBC' SetAtr 30 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_008=%Addr(City)C 'ODBC' SetAtr P_008 'BufferPtr'** Enlazar columna: País*

C 'ODBC' SetAtr 9 'Column'C 'ODBC' SetAtr 20 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_009=%Addr(Country)C 'ODBC' SetAtr P_009 'BufferPtr'** Enlazar columna: Código postal*

C 'ODBC' SetAtr 10 'Column'C 'ODBC' SetAtr 10 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_010=%Addr(Zip_Postal)C 'ODBC' SetAtr P_010 'BufferPtr'*

Figura 23. Código para el ejemplo de consulta ODBC/JDBC (Pieza 3 de 7)

126 Programación con VisualAge RPG

Page 145: c 0924494

** Enlazar columna: Localidad postal*

C 'ODBC' SetAtr 11 'Column'C 'ODBC' SetAtr 5 'BufferLen'C 'ODBC' SetAtr 1 'BufferType'C Eval P_011=%Addr(Zip_loc)C 'ODBC' SetAtr P_011 'BufferPtr'C 'ODBC' SetAtr ConnectStr 'ConnectStr'** Conectar a la base de datos y seleccionar todos los registros*

C 'ODBC' SetAtr 1 'Connect'C 'ODBC' SetAtr SelAll 'SQLQuery'C 'ODBC' SetAtr 1 'ExecuteSQL'** Buscar la primera fila de datos y visualizarla en la ventana*

C 'ODBC' SetAtr 1 'FetchNext'C Write 'Main'*

C ENDACT********************************************************************** ** Ventana . : Main ** ** Componente : PB_Prev ** ** Evento . . : Press ** ** Descripción: Buscar la fila anterior y visualizarla ** ***********************************************************************

C PB_PREV BEGACT PRESS Main*

C 'ODBC' SetAtr 1 'FetchPrior'C Write 'Main'*

C ENDACT*

Figura 23. Código para el ejemplo de consulta ODBC/JDBC (Pieza 4 de 7)

Capítulo 7. Utilización de componentes 127

Page 146: c 0924494

********************************************************************** ** Ventana . : Main ** ** Componente : PB_Next ** ** Evento . . : Press ** ** Descripción: Buscar la fila siguiente y visualizarla ** ***********************************************************************

C PB_NEXT BEGACT PRESS Main*

C 'PB_Next' Setatr 0 'Enabled'C 'ODBC' SetAtr 1 'FetchNext'C Write 'Main'C 'PB_Next' Setatr 1 'Enabled'*

C ENDACT*********************************************************************** ** Ventana . : Main ** ** Componente : PB_Insert ** ** Evento . . : Press ** ** Descripción: ** ***********************************************************************

C PB_INSERT BEGACT PRESS Main*

C Read 'Main'C 'ODBC' SetAtr 1 'InsertRow'*

C ENDACT*

Figura 23. Código para el ejemplo de consulta ODBC/JDBC (Pieza 5 de 7)

128 Programación con VisualAge RPG

Page 147: c 0924494

********************************************************************** ** Ventana . : Main ** ** Componente : PB_Delete ** ** Evento . . : Press ** ** Descripción: Suprimir la fila actual ** ***********************************************************************

C PB_DELETE BEGACT PRESS Main** Confirmar supresión de fila

C *MSG0001 Dsply mRC 9 0*

C If mRC=*YesButtonC 'ODBC' GetAtr 'CurrentRow' RowC 'ODBC' SetAtr Row 'DeleteRow'C EndIf*

C ENDACT*********************************************************************** ** Ventana . : Main ** ** Componente : PB_Update ** ** Evento . . : Press ** ** Descripción: Actualizar la fila actual ** ***********************************************************************

C PB_UPDATE BEGACT PRESS Main*

C Read 'Main'C 'ODBC' GetAtr 'CurrentRow' RowC 'ODBC' SetAtr Row 'UpdateRow'*

C ENDACT*

Figura 23. Código para el ejemplo de consulta ODBC/JDBC (Pieza 6 de 7)

Capítulo 7. Utilización de componentes 129

Page 148: c 0924494

********************************************************************** ** Ventana . : Main ** ** Componente : PB_Close ** ** Evento . . : Press ** ** Descripción: Finalizar el programa ** ***********************************************************************

C PB_CLOSE BEGACT PRESS Main*

C Move *ON *INLR*

C ENDAC*

Figura 23. Código para el ejemplo de consulta ODBC/JDBC (Pieza 7 de 7)

130 Programación con VisualAge RPG

Page 149: c 0924494

Recuadro de contorno

Utilice un recuadro de contorno alrededor de un grupo de componentes paraindicar que están relacionados.

Un recuadro de contorno no tiene etiqueta. Si en el recuadro debe aparecer unaetiqueta, utilice el componente recuadro de grupo en lugar de éste.

Para obtener información relacionada, consulte el apartado “Recuadro de grupo”en la página 79.

Atributos de componente

Bottom Handle* Height LeftParentName PartName PartType RefreshTop UserData Visible Width

Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy

Valores de altura (Height) y anchura (Width) especialesPuede crear líneas utilizando dos atributos de recuadro de contorno. Establezca elatributo Width en 1 para crear una línea vertical, y el atributo Height en 1 paracrear una línea horizontal.

Capítulo 7. Utilización de componentes 131

Page 150: c 0924494

Menú emergente

Utilice el componente menú emergente para visualizar las opciones que pertenecena un componente determinado de la interfaz. Puede añadir opciones de menú ysubmenús a los menús emergentes.

Este menú se llama “emergente” porque aparece cuando el usuario pulsa la tecla oel botón del ratón adecuados.

Nota: Las propiedades, los eventos y otros elementos de este componente sólo sepueden manipular desde su menú emergente de la vista de árbol deproyectos.

Para obtener información relacionada, consulte el apartado:v “Barra de menús” en la página 103v “Elemento de menú” en la página 104v “Submenú” en la página 166

Atributos de componente

Handle* InvName InvPName ParentNamePartName PartType UserData Visible*X Y

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarseNo hay eventos para este componente.

132 Programación con VisualAge RPG

Page 151: c 0924494

Barra de progreso

Utilice el componente barra de progreso para indicar de forma gráfica el progresode un proceso como, por ejemplo, copiar archivos, cargar una base de datos, etc.

Por ejemplo, para mostrar el progreso de copiar 100 archivos, puede establecer elatributo PBRange en 100 y el atributo PBStepSize en 10. El código podríasupervisar el proceso de copiar archivos y el indicador de barra de progresoavanzaría en pasos por cada diez archivos copiados.

En las aplicaciones Java, si el ancho de la barra de progreso es menor que la altura,la barra de progreso será vertical.

Atributos de componente

Bottom Handle* Height LeftParentName PartName PartType PBRangePBSetPos PBStep PBStepSize TopUserData Visible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy

Ejemplo de barra de progresoEn el siguiente ejemplo, el indicador de barra de progreso se actualiza cada vezque se produce una operación de lectura:*...1....+....2....+....3....+....4....+....5....+....6....+....7....+....8CSRN01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEq----*

C EVAL %setatr('win01':'WIN1':'PBRange')=10C EVAL %setatr('win01':'WIN1':'PBStepSize')=1C DO 10C Read InputC EVAL %setatr('win01':'WIN1':'PBStep')=1C EndDo*

Capítulo 7. Utilización de componentes 133

Page 152: c 0924494

Pulsador

Utilice pulsadores para proporcionar acceso a las acciones más utilizadas.

Cada componente pulsador controla una acción determinada. Cuando el usuario lopulsa, la acción se inicia inmediatamente. La etiqueta de texto del pulsadordescribe la acción que éste realiza.

Compárese con el apartado “Pulsador gráfico” en la página 77.

Atributos de componente

BackColor BackMix Border* BottomEnabled Focus FontBold FontItalicFontName FontSize FontStrike* FontUnder*ForeColor ForeMix Handle* HeightHelpEnable HighLight Label LeftParentName PartName PartType RefreshShowTips TipText Top UserDataValidate Visible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy GotFocus LostFocusMouseEnter MouseExit MouseMove PopupPress

Establecimiento de un pulsador por omisiónEn el cuaderno de propiedades de un componente pulsador, puede especificar quedesea que el pulsador sea el pulsador por omisión para la ventana que se estádiseñando. El pulsador por omisión se visualiza con un borde negro grueso y suacción asociada se lleva a cabo cuando el usuario pulsa la tecla Intro.

Nota: Sólo puede definir un pulsador por omisión por ventana. Si define más deuno, VisualAge RPG elegirá uno de ellos.

Establecimiento de un nemotécnico

Nota: Las aplicaciones Java no soportan nemotécnicos.

Para cada pulsador, utilice el atributo Label para asociar el texto a un pulsadorespecífico. Ese texto aparece en el botón.

Para especificar una clave nemotécnica para el elemento de menú, coloque elidentificador nemotécnico delante de un carácter en el texto del atributo Label. EnWindows NT/95/98, se utiliza el símbolo &. El carácter al que se ha asignado la

134 Programación con VisualAge RPG

Page 153: c 0924494

clave nemotécnica se visualiza en la interfaz con un subrayado (por ejemplo,Cancelar). El subrayado informa a los usuarios que pueden seleccionar el pulsadorpresionando la tecla del carácter subrayado en el teclado.

Asignación de teclas de mandatoPuede asignar una tecla de mandato a un pulsador. Para hacerlo, abra el cuadernode propiedades y seleccione una de las teclas de mandato de la lista disponible.

Cuando el usuario pulsa la tecla de mandato en tiempo de ejecución, tiene elmismo efecto que si hubiese pulsado el botón de ratón o una tecla en el teclado.Un evento Press se señala en el programa.

Señalización de eventosUn evento Press se señala en el programa cuando:v el usuario selecciona un pulsador.v el usuario pulsa la tecla Intro si se ha definido un pulsador por omisión.v el usuario pulsa una tecla de mandato que se ha asignado a un pulsador.

Capítulo 7. Utilización de componentes 135

Page 154: c 0924494

Botón de selección

Utilice botones de selección si desea que el usuario seleccione sólo una opción deun grupo de opciones relacionadas pero que se excluyen mutuamente. Cuando elusuario efectúa una selección, la opción seleccionada anteriormente en el grupo sedeselecciona.

Un botón de selección tiene forma circular y a su lado hay texto. Cuando estáseleccionado, contiene un punto.

No utilice botones de selección si desea que el usuario pueda seleccionar más deuna opción al mismo tiempo. En este caso, consulte el apartado “Recuadro deselección” en la página 55.

Atributos de componente

BackColor BackMix Bottom CheckedEnabled Focus FontBold FontItalicFontName FontSize FontStrike* FontUnder*ForeColor ForeMix Handle* HeightHighLight* Label Left ParentNamePartName PartType Refresh SelectIdxShowTips TipText Top UserDataVisible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy Enter MouseEnterMouseExit MouseMove Popup Select

Establecimiento de un nemotécnicoPara especificar una clave nemotécnica para el pulsador, coloque el identificadornemotécnico delante de un carácter en el texto del atributo Label. En WindowsNT/95/98, se utiliza el símbolo &. El carácter al que se ha asignado la clavenemotécnica se visualiza en la interfaz con un subrayado (por ejemplo, Azul). Elsubrayado informa a los usuarios que pueden seleccionar el botón de selecciónpulsando la tecla del carácter subrayado en el teclado.

Nota: Las aplicaciones Java no soportan nemotécnicos.

Agrupación de botones de selecciónCuando se crean botones de selección, se agrupan lógicamente de manera que laselección de un botón sólo afecta al estado de los botones del grupo de ese botón.

Por ejemplo, suponga que tiene cuatro botones de selección en una ventana dediseño. RB1 (Botón 1) y RB2 (Botón 2) se excluyen el uno al otro, al igual que RB3(Botón 3) y RB4 (Botón 4). Debe agrupar estos botones en dos grupos lógicos. La

136 Programación con VisualAge RPG

Page 155: c 0924494

figura siguiente muestra cómo se pueden agrupar estos botones de selección en laventana de diseño :

Para organizar los botones de selección en grupos lógicos:1. Organice los botones de selección como desee y, opcionalmente, coloque un

recuadro de grupo alrededor de cada grupo. (Consulte el apartado “Recuadrode grupo” en la página 79.)

2. Seleccione el componente lienzo en la ventana de diseño y pulse el botón 2 delratón.

3. Seleccione Tabuladores y Grupos... del menú emergente.Aparece la ventana Personalizar tabuladores y grupos mostrando una lista detodos los componentes de la ventana de diseño. Si es necesario, cambie eltamaño de esta ventana para ver todos los componentes.

4. Pulse el botón 1 del ratón para seleccionar el botón de selección que será elprimer botón del primer grupo. En este ejemplo, RB1 es el primer botón deselección del grupo 1.

5. Pulse el botón 2 del ratón para obtener el menú emergente para estecomponente botón de selección, y seleccione Marca de grupo.Aparece una marca de verificación X junto al botón de selección bajo lacolumna Marca de grupo.

Nota: También puede establecer la marca de grupo en el cuaderno depropiedades para el componente.

6. Utilice Control+Flecha arriba y Control+Flecha abajo para colocar RB2 despuésde RB1. Tenga en cuenta que también puede colocar estos botones dentro de lavista de árbol o utilizando los elementos de menú mover arriba y mover abajo.Asegúrese de que el atributo Group mark no se ha establecido para RB2.Esto especifica que RB2 es el segundo botón de selección del grupo 1.

7. Pulse Aceptar para cerrar la ventana.

Nota: No cierre la ventana utilizando el menú del sistema, o no se guardaránlos cambios.

Capítulo 7. Utilización de componentes 137

Page 156: c 0924494

Ahora se considera que RB1 y RB2 forman parte de un grupo, de forma queseleccionar uno de ellos sólo afectará al otro. Repita el mismo proceso para RB3 yRB4. La siguiente figura muestra la ventana Personalizar tabuladores y gruposdespués de haber agrupado los componentes:

Nota: Los topes de tabulador y las marcas de grupo también pueden establecersepara componentes concretos desde el cuaderno de propiedades de uncomponente.

Establecimiento del estado de un botón de selecciónEn el cuaderno de propiedades del botón de selección, puede indicar si el botón deselección debe estar seleccionado inicialmente o no. Sólo puede seleccionarse unbotón de selección de un grupo al mismo tiempo. Si selecciona más, sólopermanecerá seleccionado el último del grupo.

Por omisión, al crear un botón de selección, el atributo Checked se establece en 0.Esto quiere decir que el botón de selección no se establece y el estado pasa adesactivado. El botón de selección se visualiza con el círculo vacío.

Si desea crear un botón de selección que esté establecido y que el estado seaactivado, debe establecer el atributo Checked en 1. En este caso, el botón deselección se visualiza con el círculo parcialmente rellenado.

Puede establecer el atributo Checked en el cuaderno de propiedades o en elprograma.

Señalización de eventosCuando el usuario selecciona un elemento de menú, se señala un evento Select.

138 Programación con VisualAge RPG

Page 157: c 0924494

Graduador

Utilice el componente graduador si desea que el usuario visualice, establezca omodifique un valor moviendo el eje del graduador.

Los graduadores suelen utilizarse para valores con incrementos habituales, comolos segundos o los grados, o con el fin de mostrar qué porcentaje se ha realizadode una tarea.

Por omisión, el graduador se sitúa horizontalmente en el centro de un recuadrocon su eje en el lado izquierdo. Se puede visualizar una escala para mostrar lasunidades de medida del graduador.

Utilice el cuaderno de propiedades del componente graduador para:v Definir el rango de valores que un graduador puede devolver.v Colocar el graduador en posición vertical u horizontal en una ventana.v Proporcionar una escala para indicar la unidad de medida del graduador.

Atributos de componente

AddLink* AllowLink* BackColor BackMixBottom Enabled Focus FontBoldFontItalic FontName FontSize FontStrike*FontUnder* ForeColor ForeMix Handle*Height Left Maximum MinimumParentName PartName PartType RefreshRemoveLink* ShowTips TickLabel TickNumberTipText Top UserData ValueVisible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Change Create Destroy GotFocusLink* LostFocus MouseEnter MouseExitMouseMove Popup

*Nota: Consulte la descripción del evento si desea saber cuáles son lasrestricciones.

Obtención y establecimiento del valor del graduadorPuede obtener o establecer el valor del graduador utilizando el atributo Value.

Cuando obtenga el atributo Value de un graduador, asegúrese de que ha definidoun campo de resultado lo bastante grande para contener el valor devuelto.

Capítulo 7. Utilización de componentes 139

Page 158: c 0924494

Señalización de eventosEl evento Change se señala cuando cambia la posición del nivel del graduador.

Si utiliza botones de incremento para desplazar el nivel del graduador, el eventoChange se señala continuamente mientras permanezcan pulsados los botones.

Si utiliza el ratón para desplazar el nivel del graduador, se produce el eventoChange después de haber soltado el botón del ratón.

Ejemplo de graduadorEste ejemplo muestra cómo el componente graduador puede utilizarse paracontrolar el color de otros componentes utilizando el atributo BackMix. A medidaque se desplaza cada graduador, se utiliza su valor para determinar la mezcla decolor de fondo y su componente texto estático correspondiente, para mostrar laintensidad de dicho color. El color de fondo del texto estático con la etiquetaEjemplo se actualiza para mostrar la mezcla de color combinado de los trescolores.

140 Programación con VisualAge RPG

Page 159: c 0924494

********************************************************************** ** ID de programa : SLIDER ** ** Descripción . : Programa de ejemplo que muestra el componente ** graduador. ** ** Al mover cada nivel del graduador, se señala un ** evento CHANGE para ese graduador. ** La subrutina de acción CHANGE recupera el valor ** del graduador y actualiza la mezcla de color de ** fondo de su componente texto estático ** correspondiente para mostrar la intensidad de ** ese color. ** ** La mezcla de color de fondo del componente ** texto estático 'SAMPLE' también se actualiza ** para mostrar el resultado de mezclar todos los ** valores de colores. ** ***********************************************************************

H*********************************************************************** ** Ventana. . : MAIN ** ** Componente : PB_EXIT ** ** Evento . . : PRESS ** ** Descripción: Terminar el programa ** ***********************************************************************

C PB_EXIT BEGACT PRESS MAIN*

C move *on *inlr*

C ENDACT

Figura 24. Ejemplo de código en el que se utiliza el componente graduador (Pieza 1 de 4)

Capítulo 7. Utilización de componentes 141

Page 160: c 0924494

********************************************************************** ** Ventana. . : MAIN ** ** Componente : GREEN ** ** Evento . . : CHANGE ** ** Descripción: Actualizar el valor de color verde. ** ***********************************************************************

C GREEN BEGACT CHANGE MAIN*

C 'green' getatr 'Value' val 3 0C move val grnmix 3C move *blanks mix 11C movel '000:' mixC mix cat grnmix:0 mixC mix cat ':000':0 mixC 'STGreen' setatr mix 'BackMix'C exsr update*

C ENDACT********************************************************************** ** Ventana. . : MAIN ** ** Componente : BLUE ** ** Evento . . : CHANGE ** ** Descripción: Actualizar el valor de color azul. ** ***********************************************************************

C BLUE BEGACT CHANGE MAIN*

C 'blue' getatr 'Value' valC move val blumix 3C move *blanks mixC movel '000:000:' mixC mix cat blumix:0 mixC 'STBlue' setatr mix 'BackMix'C exsr update*

C ENDACT

Figura 24. Ejemplo de código en el que se utiliza el componente graduador (Pieza 2 de 4)

142 Programación con VisualAge RPG

Page 161: c 0924494

********************************************************************** ** Subrutina . . : UPDATE ** ** Descripción . : Actualiza la mezcla de color de fondo del ** componente de texto estático 'Sample' para ** mostrar el resultado de combinar los valores ** de colores de los tres graduadores. ** ***********************************************************************

C UPDATE BEGSR*

C move *blanks smpmix 11C movel redmix smpmixC smpmix cat ':':0 smpmixC smpmix cat grnmix:0 smpmixC smpmix cat ':':0 smpmixC smpmix cat blumix:0 smpmixC 'Sample' setatr smpmix 'BackMix'*

C ENDSR********************************************************************** ** Ventana. . : MAIN ** ** Componente : RED ** ** Evento . . : CHANGE ** ** Descripción: Actualizar el valor de color rojo. ** ***********************************************************************

C RED BEGACT CHANGE FRA0000B*

C 'red' getatr 'Value' valC move val redmix 3C move *blanks mixC movel redmix mixC mix cat ':000:000':0 mixC 'STRed' setatr mix 'BackMix'C exsr update*

C ENDACT

Figura 24. Ejemplo de código en el que se utiliza el componente graduador (Pieza 3 de 4)

Capítulo 7. Utilización de componentes 143

Page 162: c 0924494

********************************************************************** ** Ventana. . : MAIN ** ** Componente : MAIN ** ** Evento . . : CREATE ** ** Descripción: Inicializar la mezcla de color ** ***********************************************************************

C MAIN BEGACT CREATE MAIN*

C move '000' grnmixC move '000' blumixC move '000' redmix*

C ENDACT

Figura 24. Ejemplo de código en el que se utiliza el componente graduador (Pieza 4 de 4)

144 Programación con VisualAge RPG

Page 163: c 0924494

Selector cíclico

Utilice el componente selector cíclico para visualizar, de forma secuencial, ungrupo de opciones relacionadas, pero que se excluyen mutuamente, que tienen unorden consecutivo lógico; por ejemplo, los meses del año. Las opciones sevisualizan como si estuvieran organizadas en forma de anillo. El usuario puedemover (o “girar”) las opciones pulsando la flecha hacia arriba para ir al valorsuperior siguiente o la flecha hacia abajo para ir al valor inferior siguiente.También puede escribir una opción directamente en el campo de entrada delselector cíclico.

Atributos de componente

AddItemEnd Alignment* BackColor BackMixBottom Enabled Focus FontBoldFontItalic FontName FontSize FontStrike*FontUnder* ForeColor ForeMix Handle*Height Left Maximum MinimumParentName PartName PartType ReadOnlyRefresh RemoveItem ShowTips TextTipText Top UserData ValueVisible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Change Create Destroy GotFocusLink* LostFocus MouseEnter MouseExitMouseMove Popup SpinDown SpinEndSpinUp

*Nota: Consulte la descripción del evento si desea saber cuáles son lasrestricciones.

Establecimiento de valores del selector cíclicoEl tipo de datos del selector cíclico determina el método utilizado para establecerlos valores del selector cíclico.

Para especificar los valores permitidos para un selector cíclico, establezca losatributos Maximum y Minimum.

Para establecer los valores iniciales de la lista de selectores cíclicos de un botón deselector cíclico de caracteres, establezca el atributo AddItemEnd para cadaelemento que desee añadir. Añada los elementos en el orden en que desea queaparezcan, porque los elementos del selector cíclico de caracteres no se clasificanautomáticamente.

Capítulo 7. Utilización de componentes 145

Page 164: c 0924494

Obtención del valor del selector cíclicoEl atributo que se utiliza para recuperar el valor que se selecciona en un selectorcíclico depende del tipo de selector cíclico.v Para los selectores cíclicos de caracteres, utilice el atributo Text.v Para los selectores cíclicos numéricos, utilice el atributo Value. Este atributo

devuelve un valor entre los valores mínimo y máximo inclusive especificadospara el selector cíclico.

Cómo evitar la entrada de datos por parte del usuarioPuede impedir que el usuario escriba un valor directamente en el campo asociadoal selector cíclico estableciendo el atributo ReadOnly en el cuaderno depropiedades del selector cíclico o estableciendo este atributo en 1 en el programa.

Ejemplo de selector cíclicoEste ejemplo muestra cómo establecer y obtener los valores para un selector cícliconumérico y de caracteres. Cuando se inicia el programa, se inserta una lista inicialen cada selector cíclico. Cuando se selecciona el pulsador Copiar, el valor de cadaselector cíclico se copia al componente campo de entrada asociado.

Accione el pulsador Cerrar para terminar el programa.

146 Programación con VisualAge RPG

Page 165: c 0924494

********************************************************************** ** ID de programa : SPIN ** ** Descripción . : Programa de ejemplo que muestra el componente ** selector cíclico. ** ** Se utiliza un selector cíclico de caracteres y ** otro numérico para mostrar cómo se inicializan ** y cómo se recuperan sus valores. ** ***********************************************************************

H*

DDAY S 10A DIM(7) PERRCD(1) CTDATA*********************************************************************** ** Ventana. . : MAIN ** ** Componente : PB_COPY ** ** Evento . . : PRESS ** ** Descripción: Copiar el valor de cada botón selector cíclico a ** su componente campo de entrada correspondiente. ** ***********************************************************************

C PB_COPY BEGACT PRESS MAIN*

C 'SPB1' Getatr 'Value' tmp2N 2 0C 'EF1' Setatr tmp2N 'Text'*

C 'SPB2' Getatr 'Text' tmp 10C 'EF2' Setatr tmp 'Text'*

C ENDACT

Figura 25. Ejemplo de código en el que se utiliza el componente selector cíclico (Pieza 1 de2)

Capítulo 7. Utilización de componentes 147

Page 166: c 0924494

********************************************************************** ** Ventana. . : MAIN ** ** Componente : MAIN ** ** Evento . . : CREATE ** ** Descripción: Centrar la ventana en la pantalla e ** inicializar los selectores cíclicos. ** ***********************************************************************

C MAIN BEGACT CREATE MAIN** Inicializar el selector cíclico de caracteres con los días* de la semana a partir de la matriz DAY

C Do 7 I 2 0C 'SPB2' Setatr day(i) 'AddItemEnd'C EndDo** Inicializar el selector cíclico numérico

C 'SPB1' Setatr 1 'Minimum'C 'SPB1' Setatr 10 'Maximum'*

C ENDACT********************************************************************** ** Ventana. . : MAIN ** ** Componente : PB_EXIT ** ** Evento . . : PRESS ** ** Descripción: Terminar el programa ** ***********************************************************************

C PB_EXIT BEGACT PRESS MAIN*

C Move *On *INLR*

C ENDACT**CTDATA DAYDomingoLunesMartesMiércolesJuevesViernesSábado

Figura 25. Ejemplo de código en el que se utiliza el componente selector cíclico (Pieza 2 de2)

148 Programación con VisualAge RPG

Page 167: c 0924494

Texto estático

Utilice el componente texto estático como etiqueta de otros componentes, porejemplo, como solicitud de un componente campo de entrada. Los componentestexto estático no aceptan la entrada de datos por parte del usuario. En lasaplicaciones Java, el texto estático se visualiza únicamente en una sola línea.

Atributos de componente

Alignment BackColor BackMix BottomDataType DragEnable* DropEnable* EnabledFontBold FontItalic FontName FontSizeFontStrike* FontUnder* ForeColor ForeMixHandle* Height Label LeftParentName PartName PartType RefreshShowTips TipText Top UserDataVisible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Click Create DblClick DestroyDrop Link* MouseDown MouseEnterMouseExit MouseMove MouseUp Popup

*Nota: Consulte la descripción del evento si desea saber cuáles son lasrestricciones.

Cambio del texto de un componente texto estáticoEl componente texto estático es un área rectangular en la que se coloca el texto.Utilice el atributo Label para cambiar el texto de un elemento de texto estático.

Si cambia el texto de tal manera que sea más largo que el texto original, el nuevotexto se recortará en los bordes del rectángulo que lo rodea. El texto también serecortará si cambia los atributos FontName y FontSize a un font o tamaño mayor.

Cuando cambie el texto del programa, asegúrese de que el componente textoestático en el Diseñador GUI es lo bastante grande para mostrar el texto nuevo.

Obtención de valores de texto estáticoPara obtener el valor de un componente de texto estático, debe especificar elatributo Label. Si está obteniendo el valor de un componente texto estáticonumérico, el campo que recibe el valor también debe definirse como numérico.

Capítulo 7. Utilización de componentes 149

Page 168: c 0924494

Obtención y establecimiento de información para una ventanaDurante la compilación, el compilador define de manera implícita los campos delprograma con el mismo nombre que el componente texto estático y con el mismotipo de datos y longitud. Mediante los códigos de operación READ y WRITE conun nombre de ventana especificado en el factor 2, el valor del atributo Label secopia automáticamente en estos campos o desde ellos. Los códigos de operaciónREAD y WRITE son muy útiles si se tienen muchos componentes texto estático enla interfaz de usuario, para que no tenga que establecer los atributos y obtener unvalor de forma repetitiva.

Consulte el “Capítulo 3. Programación con componentes” en la página 25 si deseamás información.

Edición de la salidaPuede editar el contenido de un componente texto estático si el tipo de datos esnumérico. Consulte el “Capítulo 11. Edición de la salida” en la página 229 paraobtener una descripción de la edición.

150 Programación con VisualAge RPG

Page 169: c 0924494

Barra de estado

Utilice el componente barra de estado para proporcionar información adicionalsobre un proceso o una acción de la ventana. Puede crear hasta cinco paneles parala barra de estado. El componente barra de estado proporciona al componenteventana mayor flexibilidad que el atributo StatusBar.

Por omisión, la barra de estado se crea en la parte inferior de la ventana. Noobstante, puede utilizar el cuaderno de propiedades para colocarla en la partesuperior. También puede establecer el estilo del borde, el número de paneles y laalineación del texto.

Atributos de componente

Handle* ParentName PartName PartTypeSBIndex SBLabel SBPanes UserDataVisible

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy

Ejemplo de Barra de estadoEn el siguiente ejemplo, la etiqueta de la barra de estado se actualiza mientras selleva a cabo el proceso inicial:*...1....+....2....+....3....+....4....+....5....+....6....+....7....+....8CSRN01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEq----*

C STBAR BEGACT CREATE MAINC 'STBAR' SETATR 'Wait...' 'SBLABEL'** Efectuar un proceso.*

C DOC ...C ENDDO** Borrar la etiqueta de barra de estado.*

C 'STBAR' SETATR *BLANKS 'SBLABEL'C ENDACT*

Capítulo 7. Utilización de componentes 151

Page 170: c 0924494

Subarchivo

Utilice el componente subarchivo para visualizar una lista de registros, cada unode los cuales consta de uno o más campos.

La función del componente subarchivo es similar a la de un subarchivo deAS/400

®

. El usuario puede desplazar el contenido de la lista en sentido horizontalo vertical utilizando las barras de desplazamiento del subarchivo.

Para crear un campo de entrada de subarchivo, añada un campo de la ventanaDefinir campos de referencia o de la paleta de componentes en el componentesubarchivo. También puede añadir campos utilizando el cuaderno de propiedades.

Nota: El componente subarchivo sólo se puede colocar en una página de cuadernocon lienzo o en una ventana con lienzo.

Atributos de componente

AddItemEnd AllowEdit AutoSelect BackColorBackMix Bottom ButtonIdx ButtonsButtonTip CapsLock CellBGClr CellBGMixCellFGClr CellFGMix ColBGClr ColBGMixColFGClr ColFGMix ColNumber ColWidthCount DeSelect EnableBtn EnabledExtSelect* FirstSel Focus FontAreaFontBold FontItalic FontName FontSizeFontStrike* FontUnder* ForeColor ForeMixHandle* HdgBGClr HdgBGMix HdgFGClrHdgFGMix HdgIdx HdgText HeightHidden HRule Index ItemCountLeft MultSelect NbrOfSel OpenEditPageSize ParentName PartName PartTypeRemoveItem RowBGClr RowBGMix RowFGClrRowFGMix Scale Selected SelectItemSelectList SetTop SflNxtChg ShowTipsSizeToFit StartAt TipText TopTopRecord UserData Visible VRuleWidth

* Nota:: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Change ColSelect Create DestroyEnter FirstRec GotFocus KeyPressLastRec LostFocus MouseEnter MouseExitMouseMove NextRec PageDown PageEndPageTop PageUp Popup PrevRecSelect VKeyPress

152 Programación con VisualAge RPG

Page 171: c 0924494

Creación de un componente subarchivoSólo puede crear un componente subarchivo en un componente lienzo.

Número máximo de campos por subarchivoPuede definir un máximo de 99 campos para un subarchivo.

Códigos de operación para manipular componentessubarchivo

Además de utilizar atributos para controlar un subarchivo, puede utilizar varioscódigos de operación que afecten al componente subarchivo. Especifique el nombredel subarchivo en el factor 2. No lo ponga entre comillas.

Están soportados los siguientes códigos de operación. Para obtener una descripcióncompleta de cada uno de ellos, consulte la publicación VisualAge RPG Manual deconsulta del lenguaje, SC10-3066-01 (SC09-2451-01), o la ayuda dependiente delenguaje.

CódigoOperación

CHAINLee un registro de un subarchivo especificando un índice.

CLEARBorra todos los registros del subarchivo.

DELETESuprime un registro del subarchivo. Todos los registros que siguen alregistro suprimido ascienden una posición.

READCLee un registro si ha cambiado el valor de cualquiera de los campos deentrada del registro.

READSLee un registro seleccionado del subarchivo. Los usuarios puedenseleccionar un registro mediante el ratón o el teclado. Una vez leído elregistro, se deselecciona.

UPDATEActualiza un registro de subarchivo existente. Debe haberse leído unregistro antes de que pueda utilizarse este código de operación.

WRITEAñade un registro nuevo al subarchivo.

Carga de un subarchivoPara visualizar información en un componente subarchivo, la información se grabade registro en registro en el componente subarchivo. Los campos de subarchivoque se definieron en el Diseñador GUI para el componente subarchivo seestablecen en los valores deseados, y la operación WRITE se realiza en el formatode registro de subarchivo.

Determinación del tamaño de subarchivoA diferencia del subarchivo AS/400, el componente subarchivo no tiene tamañosde página de subarchivo. El número de registros que un subarchivo puedecontener está limitado por la cantidad de memoria en la estación de trabajo. El

Capítulo 7. Utilización de componentes 153

Page 172: c 0924494

tamaño de página de subarchivo (es decir, el número de registros que se muestrana la vez) se determina al crear el subarchivo en el Diseñador GUI.

Obtención de la cuenta de registrosPara determinar cuántos registros están en un archivo actualmente, utilice elatributo Count.

Lectura y actualización de registrosLos registros de un componente subarchivo pueden actualizarse o suprimirse. Paraactualizar registros, primero debe situar el subarchivo en el registro que deseaactualizar. Puede situar el subarchivo mediante una operación CHAIN, READC oREADS. Estas operaciones hacen que los valores de campo del registro recuperadose asignen a los campos de programa correspondientes para el formato de registrode subarchivo. Luego, el programa puede modificar los valores de campo.

Una operación UPDATE ejecutada en el componente subarchivo envía acontinuación los valores actuales de los campos asociados devueltos al subarchivo.Utilice CHAIN para seleccionar registros según la posición relativa en unsubarchivo, READC para seleccionar registros que el usuario ha modificado en lapantalla de subarchivo, y READS para los registros que el usuario ha seleccionado.

El ejemplo siguiente muestra cómo la operación READS efectúa un bucle paraobtener todos los registros seleccionados en un subarchivo y cómo los procesa yactualiza, uno a uno. Se codifica en una subrutina de acción para el evento Presspara un pulsador denominado Informe.

Cambio de campos de subarchivo

Nota: El usuario no puede cambiar un campo de subarchivo si se establece comode sólo lectura.

Antes de que el usuario pueda cambiar un campo en un subarchivo, el usuario dela aplicación o usted en el programa debe abrirlo:

...C REPORT BEGACT PRESS WIN1*

C READS SUBF1 99*

C *IN99 DOWEQ *OFF*** Para el registro seleccionado, procesarlo y marcarlo* como 'Informado' en la pantalla de subarchivo.*

C MOVEL '(Reported)' SF1NAME*

C UPDATE SUBF1*

C READS SUBF1 99C END*

C ENDACT

Figura 26. Ejemplo de codificación de lectura y modificación de registros

154 Programación con VisualAge RPG

Page 173: c 0924494

1. El usuario selecciona el campo con el puntero del ratón y pulsa el botón 1 delratón mientras mantiene pulsada la tecla Alt. A continuación, el usuario puedeutilizar las teclas de tabulador y retroceso de tabulador para desplazarse pordiferentes campos en el mismo registro, y utilizar las teclas de flecha arriba yflecha abajo para desplazarse a registros distintos.

2. Para abrir un campo para editarlo en el programa:a. Utilice el atributo Index para indicar qué registro contiene el campo que va

a editarse.b. Establezca el atributo ColNumber para indicar el número de columna del

campo que va a editarse.c. Establezca el valor del atributo OpenEdit en 1 para abrir el campo con el

propósito de editarlo. (Puede establecer este valor del atributo en 0 paracerrar cualquier campo que esté abierto actualmente para editarse.)

Utilice la operación READC para determinar si el usuario ha cambiado algúncampo en el subarchivo.

Campos ocultosEn el cuaderno de propiedades del componente subarchivo, puede establecer quecampos de subarchivo estén Ocultos para que no se visualicen. Por ejemplo, unregistro de subarchivo puede contener información de clave de registro en uncampo oculto. El campo oculto no puede verse, pero se devuelve al programa conel registro de subarchivo.

Formato de campos de subarchivoLos campos de un subarchivo pueden resaltarse de varias maneras. Puedenestablecerse colores de primer plano y de fondo tanto para cabeceras de subarchivocomo para campos de subarchivo concretos. Pueden colocarse separadores de líneahorizontal o vertical en un subarchivo.

Vaya a “Capítulo 11. Edición de la salida” en la página 229 para obtener másinformación.

Habilitación de la tabulaciónUtilice el diálogo Personalizar tabuladores y grupos para habilitar la tabulación enun componente subarchivo. Pulse con el botón derecho del ratón en el componentelienzo de la ventana que contiene el componente subarchivo. SeleccioneTabuladores y grupos en el menú emergente. Aparecerá el diálogo Personalizartabuladores y grupos. Para establecer o borrar el valor de tabulación, pulse con elbotón derecho del ratón en el nombre del componente y seleccione la opción demenú Tabulador.

Ejemplo de subarchivoEn el siguiente ejemplo, se utiliza un componente subarchivo para visualizarregistros de un archivo de base de datos en un sistema AS/400. En lugar derellenar el subarchivo con todos los registros de la base de datos, se proporcionanpulsadores de navegación (FirstRec, LastRec, PageTop, PageUp, PageDown,PrevPage, NextPage) con el fin de controlar el desplazamiento por los registrosdentro del subarchivo.

Cuando accione el pulsador Select, se utiliza el código de operación READS paradeterminar qué registro se ha seleccionado, y el valor del campo CUSTNO sevisualiza en el componente texto estático. Además se abre el primer campo delregistro para editarlo.

Capítulo 7. Utilización de componentes 155

Page 174: c 0924494

Seleccione el elemento de menú Exit para finalizar el programa.

********************************************************************** ** ID de programa : SUBFILE ** ** Descripción . : Programa de ejemplo que muestra el componente ** subarchivo. ** ** Este programa de ejemplo requiere un archivo ** físico de base de datos en el AS/400 ** denominado CUSTOMER. ** ***********************************************************************

HFCUSTOMER IF E DISK REMOTE INFDS(INFDS) BLOCK(*Yes)** INFDS para el archivo de base de datos. FileSize contendrá* el número de registros en el archivo cuando éste se abrió.

DINFDS DSDFileSize 156 159B 0*********************************************************************** ** Subrutina . . : *INZSR ** ** Descripción . : Inicializar las variables de trabajo. ** ***********************************************************************

C *INZSR BEGSR*

C Z-Add 10 PageSize 2 0C Z-Add 1 CurRec 6 0C FileSize Sub PageSize LastPage 6 0C Add 1 LastPage*

C ENDSR* *

Figura 27. Ejemplo de codificación utilizando el componente subarchivo (Pieza 1 de 10)

156 Programación con VisualAge RPG

Page 175: c 0924494

********************************************************************** ** Subrutina . . : NEXTPAGE ** ** Descripción . : Obtener la página siguiente de los registros ** de la base de datos. ** ***********************************************************************

C NEXTPAGE BEGSR*

C add PageSize CurRec*

C CurRec IfGt FileSizeC Sub PageSize CurRec*

C ElseC Exsr FillPageC 'SFl1' setatr 2 'BUTTONIDX'C 'SFL1' setatr 1 'ENABLEBTN'C EndIf*

C ENDSR

Figura 27. Ejemplo de codificación utilizando el componente subarchivo (Pieza 2 de 10)

Capítulo 7. Utilización de componentes 157

Page 176: c 0924494

********************************************************************** ** Subrutina . . : PREVPAGE ** ** Descripción . : Devolver la página anterior de registros de la ** base de datos. ** ***********************************************************************

C PREVPAGE BEGSR*

C Sub PageSize CurRec*

C CurRec IfLe *zeroC Add PageSize CurRec*

C ElseC Exsr FillPageC 'SFl1' setatr 5 'BUTTONIDX'C 'SFL1' setatr 1 'ENABLEBTN'C EndIf*

C ENDSR********************************************************************** ** Subrutina . . : FILLPAGE ** ** Descripción . : Rellenar el componente subarchivo con una página ** de registros de la base de datos. ** ***********************************************************************

C FILLPAGE BEGSR*

C Clear Sfl1C CurRec Setll customerC Z-Add 1 count 2 0C Read customer 9999*

C *in99 DoWeq *offC count AndLE PageSizeC Write Sfl1*

C If %Getatr('Main':'HILITE':'Checked')=1C 'SFL1' Setatr Count 'Index'C 'SFL1' Setatr 1 'ColNumber'C 'SFL1' Setatr *DarkGreen 'CellFGClr'C 'SFL1' Setatr 2 'ColNumber'C 'SFL1' Setatr *DarkPink 'CellFGClr'C 'SFL1' Setatr 3 'ColNumber'C 'SFL1' Setatr *DarkBlue 'CellFGClr'C EndIf

Figura 27. Ejemplo de codificación utilizando el componente subarchivo (Pieza 3 de 10)

158 Programación con VisualAge RPG

Page 177: c 0924494

*C Add 1 countC Read customer 9999C EndDo*

C Read customer 9999*

C CurRec ifeq 1C 'SFl1' setatr 1 'BUTTONIDX'C 'SFL1' setatr 0 'ENABLEBTN'C 'SFl1' setatr 2 'BUTTONIDX'C 'SFL1' setatr 0 'ENABLEBTN'C 'SFl1' setatr 5 'BUTTONIDX'C 'SFL1' setatr 1 'ENABLEBTN'C 'SFl1' setatr 6 'BUTTONIDX'C 'SFL1' setatr 1 'ENABLEBTN'C endif*

C *in99 ifeq *onC CurRec oreq LastPageC 'SFl1' setatr 1 'BUTTONIDX'C 'SFL1' setatr 1 'ENABLEBTN'C 'SFl1' setatr 2 'BUTTONIDX'C 'SFL1' setatr 1 'ENABLEBTN'C 'SFl1' setatr 5 'BUTTONIDX'C 'SFL1' setatr 0 'ENABLEBTN'C 'SFl1' setatr 6 'BUTTONIDX'C 'SFL1' setatr 0 'ENABLEBTN'C endifC ENDSR*********************************************************************** ** Ventana. . : MAIN ** ** Componente : MAIN ** ** Evento . . : CREATE ** ** Descripción: Obtener la primera página de los registros. ** ***********************************************************************

C MAIN BEGACT CREATE MAIN*

C Exsr FillPage*

C 'SFL1' Setatr *Green 'HdgBGClr'C 'SFL1' Setatr *Black 'HdgFGClr'C 'SFL1' Setatr 1 'ColNumber'

Figura 27. Ejemplo de codificación utilizando el componente subarchivo (Pieza 4 de 10)

Capítulo 7. Utilización de componentes 159

Page 178: c 0924494

*C 'MAIN' Setatr 1 'Visible'C 'SFL1' Setatr 1 'BUTTONIDX'C 'SFL1' Setatr '*MSG0001' 'BUTTONTIP'C 'SFL1' Setatr 0 'ENABLEBTN'C 'SFL1' Setatr 2 'BUTTONIDX'C 'SFL1' Setatr '*MSG0002' 'BUTTONTIP'C 'SFL1' Setatr 0 'ENABLEBTN'C 'SFL1' Setatr 3 'BUTTONIDX'C 'SFL1' Setatr 0 'ENABLEBTN'C 'SFL1' Setatr 4 'BUTTONIDX'C 'SFL1' Setatr 0 'ENABLEBTN'C 'SFL1' Setatr 5 'BUTTONIDX'C 'SFL1' Setatr '*MSG0004' 'BUTTONTIP'C 'SFL1' Setatr 6 'BUTTONIDX'C 'SFL1' Setatr '*MSG0005' 'BUTTONTIP'*

C ENDACT* *********************************************************************** ** Ventana. . : MAIN ** ** Componente : PB_SELECT ** ** Evento . . : PRESS ** ** Descripción: Leer el registro de subarchivo seleccionado. ** Se actualiza el componente de texto estático ** 'Selected' para mostrar el número de cliente ** seleccionado. ** Se abre el primer campo del subarchivo para su ** edición. ** ***********************************************************************

C PB_SELECT BEGACT PRESS MAIN*

C Reads sfl1 27*

C *in27 IfEq *offC 'Selected' Setatr custno 'Label'C 'SFL1' Setatr 1 'ColNumber'C 'SFL1' Setatr 1 'OpenEdit'C EndIf*

C ENDACT

Figura 27. Ejemplo de codificación utilizando el componente subarchivo (Pieza 5 de 10)

160 Programación con VisualAge RPG

Page 179: c 0924494

********************************************************************** ** Ventana. . : MAIN ** ** Componente : HRULE ** ** Evento . . : MENUSELECT ** ** Descripción: ** ***********************************************************************

C HRULE BEGACT MENUSELECT MAIN*

C If %Getatr('Main':'HRULE':'Checked')=1C 'SFL1' Setatr 0 'HRule'C 'HRULE' Setatr 0 'Checked'*

C ElseC 'SFL1' Setatr 1 'HRule'C 'HRULE' Setatr 1 'Checked'C EndIf*

C ENDACT********************************************************************** ** Ventana. . : MAIN ** ** Componente : VRULE ** ** Evento . . : MENUSELECT ** ** Descripción: ** ***********************************************************************

C VRULE BEGACT MENUSELECT MAIN*

C If %Getatr('Main':'VRULE':'Checked')=1C 'SFL1' Setatr 0 'VRule'C 'VRULE' Setatr 0 'Checked'*

C ElseC 'SFL1' Setatr 1 'VRule'C 'VRULE' Setatr 1 'Checked'C EndIf*

C Exsr FillPage*

C ENDACT

Figura 27. Ejemplo de codificación utilizando el componente subarchivo (Pieza 6 de 10)

Capítulo 7. Utilización de componentes 161

Page 180: c 0924494

********************************************************************** ** Ventana. . : MAIN ** ** Componente : HILITE ** ** Evento . . : MENUSELECT ** ** Descripción: ** ***********************************************************************

C HILITE BEGACT MENUSELECT MAIN*

C If %Getatr('Main':'HILITE':'Checked')=1C Eval %Setatr('Main':'HILITE':'Checked')=0*

C ElseC Eval %Setatr('Main':'HILITE':'Checked')=1C EndIf*

C Exsr FillPage*

C ENDACT********************************************************************** ** Ventana. . : MAIN ** ** Componente : SFL1 ** ** Evento . . : PAGETOP ** ** Descripción: ** ***********************************************************************

C SFL1 BEGACT PAGETOP MAIN*

C Z-Add 1 CurRecC Exsr FillPage*

C ENDACT

Figura 27. Ejemplo de codificación utilizando el componente subarchivo (Pieza 7 de 10)

162 Programación con VisualAge RPG

Page 181: c 0924494

********************************************************************** ** Ventana. . : MAIN ** ** Componente : SFL1 ** ** Evento . . : PAGEUP ** ** Descripción: ** ***********************************************************************

C SFL1 BEGACT PAGEUP MAIN*

C exsr PrevPage*

C ENDACT*********************************************************************** ** Ventana. . : MAIN ** ** Componente : SFL1 ** ** Evento . . : LASTREC ** ** Descripción: ** ***********************************************************************

C SFL1 BEGACT LASTREC MAIN*

C FileSize Sub PageSize CurRecC Add 1 CurRec*

C CurRec IfLt 1C Z-Add 1 CurRecC EndIf*

C Exsr FillPage*

C 'SFL1' setatr 1 'BUTTONIDX'C 'SFL1' setatr 1 'ENABLEBTN'C 'SFL1' setatr 2 'BUTTONIDX'C 'SFL1' setatr 1 'ENABLEBTN'C 'SFL1' setatr 5 'BUTTONIDX'C 'SFL1' setatr 0 'ENABLEBTN'C 'SFL1' setatr 6 'BUTTONIDX'C 'SFL1' setatr 0 'ENABLEBTN'C ENDACT

Figura 27. Ejemplo de codificación utilizando el componente subarchivo (Pieza 8 de 10)

Capítulo 7. Utilización de componentes 163

Page 182: c 0924494

********************************************************************** ** Ventana. . : MAIN ** ** Componente : SFL1 ** ** Evento . . : PAGEDOWN ** ** Descripción: ** ***********************************************************************

C SFL1 BEGACT PAGEDOWN MAIN*

C Exsr NextPage*

C ENDACT********************************************************************** ** Ventana. . : MAIN ** ** Componente : SFL1 ** ** Evento . . : FIRSTREC ** ** Descripción: ** ***********************************************************************

C SFL1 BEGACT FIRSTREC MAIN*

C Z-Add 1 CurRecC Exsr FillPage*

C 'SFL1' setatr 1 'BUTTONIDX'C 'SFL1' setatr 0 'ENABLEBTN'C 'SFL1' setatr 2 'BUTTONIDX'C 'SFL1' setatr 0 'ENABLEBTN'C 'SFL1' setatr 5 'BUTTONIDX'C 'SFL1' setatr 1 'ENABLEBTN'C 'SFL1' setatr 6 'BUTTONIDX'C 'SFL1' setatr 1 'ENABLEBTN'C ENDACT

Figura 27. Ejemplo de codificación utilizando el componente subarchivo (Pieza 9 de 10)

164 Programación con VisualAge RPG

Page 183: c 0924494

Señalización de eventosEl evento Select se señala cuando:v Un usuario selecciona un elemento que ya está en un subarchivo.v Selecciona un elemento de la lista en el programa.v Un usuario selecciona un elemento que ya ha sido seleccionado.

El evento Enter se señala cuando:v Un usuario efectúa una doble pulsación sobre un elemento que está en el

subarchivo.v Un usuario pulsa la tecla Intro cuando el subarchivo tiene el foco y se ha

seleccionado un elemento.

En la subrutina de acción para estos eventos, puede utilizar el código de operaciónREADS para determinar qué elemento se ha seleccionado.

********************************************************************** ** Ventana. . : MAIN ** ** Componente : EXIT ** ** Evento . . : MENUSELECT ** ** Descripción: ** ***********************************************************************

C EXIT BEGACT MENUSELECT MAIN*

C Move *on *inlr*

C ENDACT

Figura 27. Ejemplo de codificación utilizando el componente subarchivo (Pieza 10 de 10)

Capítulo 7. Utilización de componentes 165

Page 184: c 0924494

Submenú

Utilice un submenú para:v Iniciar un menú en cascada nuevo a partir de una opción de menú de un menú

ya existente.v Iniciar un menú desplegable a partir de una opción de menú de la barra de

menús.

Tras crear un submenú, puede añadirle opciones de menú colocando componentesopción de menú, pero solamente en la vista de árbol.

Nota: Las propiedades, los eventos y otros elementos de este componente sólo sepueden manipular desde su menú emergente de la vista de árbol deproyectos.

Para obtener información relacionada, consulte el apartado “Elemento de menú” enla página 104.

Atributos de componente

ParentName PartName PartType UserData

Eventos a los que puede aplicarse

Create Destroy

166 Programación con VisualAge RPG

Page 185: c 0924494

Temporizador

Utilice el componente temporizador si el programa debe realizar determinadasoperaciones en intervalos de tiempo preestablecidos. Por ejemplo, puede utilizarlopara cerrar una ventana o para finalizar una aplicación después de un periododeterminado de inactividad.

El componente temporizador cuenta unidades de tiempo, hace un seguimiento delintervalo de tiempo preestablecido que transcurre entre dos eventos y desencadenael segundo evento cuando haya pasado el tiempo necesario.

Cuando se crea un componente temporizador en el constructor GUI, elcomponente aparece en forma de icono en la ventana de diseño. Sin embargo, en elcuaderno de propiedades de un componente temporizador, puede especificar queno desea que el icono se visualice mientras el programa se ejecuta.

Nota: No utilice el componente temporizador cuando precise un control exacto deltiempo. El evento Tick puede no producirse en el intervalo exacto que haespecificado, ya que hay otros programas ejecutándose en el sistema.

Atributos de componente

AddLink* AllowLink* Bottom IntervalLeft Multiplier ParentName PartNamePartType RemoveLink* TimerMode TimerTicksTop UserData Visible

* Nota:: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy Link* Tick

* Nota:: Consulte la descripción del evento si desea saber cuáles son lasrestricciones.

Visualización del icono TemporizadorPor omisión, el atributo Visible se establece en 1 de tal manera que el icono detemporizador se visualiza mientras está ejecutándose el programa. Si no desea queeste icono se visualice, establezca este atributo en 0.

Establecimiento del intervaloEl intervalo del temporizador se expresa en milisegundos. Cuando ha transcurridoel intervalo se señala un evento Tick de temporizador. Puede establecer esteintervalo en el cuaderno de propiedades del componente temporizador. Tambiénpuede establecerse en el programa utilizando el atributo Interval.

Nota: El intervalo mínimo del temporizador es de 100 milisegundos.

Capítulo 7. Utilización de componentes 167

Page 186: c 0924494

El componente temporizador tiene un atributo Multiplier. Al establecer esteatributo, puede determinar cuántas veces transcurre el valor del intervalo antes deque se genere un evento Tick de temporizador. El valor de multiplicador seestablece en 1, de manera que el temporizador genere un evento Tick al final decada intervalo.

Generación de eventos TickCuando se inicia un temporizador su valor de intervalo se restablece a cero.Cuando se alcanza el valor de intervalo, el temporizador genera un evento Tick yactualiza el valor del intervalo.

Obtención del valor de temporizadorCada vez que el temporizador genere un evento Tick, su valor se incrementa enuno. Utilice el atributo Value para obtener el valor actual del temporizador. Puedeestablecer el valor del temporizador en el cuaderno de propiedades o en elprograma.

Control del temporizador utilizando modalidades detemporizador

Utilice el atributo TimerMode para controlar el temporizador.

Establezca TimerMode en 1 para iniciar el temporizador. Iniciar el temporizadorhace que empiece a generar eventos Tick, y su atributo Value se incrementacuando se alcanza el valor del intervalo.

Establezca TimerMode en 2 para detener el temporizador. Cuando se pare eltemporizador, cesará de generar eventos Tick y no se actualizará su valor.

Ejemplo de temporizadorEn este ejemplo, un componente texto estático se desplaza en la ventana para cadaevento Tick de temporizador.

Al accionar el pulsador Start, la modalidad de temporizador se establece en 1. Estoinicia el temporizador y genera eventos Tick. Durante el proceso del evento Tick,se calculan nuevas coordenadas para el componente texto estático y el componentese establece en la nueva ubicación.

Cuando accione el pulsador Detener, TimerMode se establecerá en 2. Esto detieneel temporizador.

Accione el pulsador Close para terminar el programa.

168 Programación con VisualAge RPG

Page 187: c 0924494

********************************************************************** ** ID de programa : TIMER ** ** Descripción . : Programa de ejemplo que muestra el componente ** temporizador moviendo un componente texto ** estático en una ventana cada vez que se produce ** un 'Tick' en el temporizador. ** ***********************************************************************

H** Declarar atributos de sistema de tamaño de pantalla

D%DspHeight S 4 0D%DspWidth S 4 0** Declarar nuevos atributos de evento de tamaño

D%NewHeight S 4 0D%NewWidth S 4 0** Definir variables de trabajo

DminX S 4 0 INZ(0)DmaxX S 4 0DminY S 4 0DmaxY S 4 0DxChange S 4 0 INZ(5)DyChange S 4 0 INZ(5)*

Figura 28. Ejemplo de código en el que se utiliza el componente temporizador (Pieza 1 de 6)

Capítulo 7. Utilización de componentes 169

Page 188: c 0924494

********************************************************************** ** Ventana . : FRA0000B ** ** Componente : FRA0000B ** ** Evento . . : CREATE ** ** Descripción: Centrar la ventana en la pantalla. ** ** Calcular los valores iniciales. ** Dado que el atributo de altura del componente ** ventana incluye la barra de título, restamos la ** altura de la barra de título para que el componente ** texto estático permanezca dentro del marco de la ** ventana. ** ** Para SVGA, este valor es de unos 20 pixels. ** Puede ajustarse para otras resoluciones. ** ***********************************************************************

C FRA0000B BEGACT CREATE FRA0000B** Obtener altura y anchura de ventana inicial

C 'FRA0000B' getatr 'Height' winHeight 4 0C 'FRA0000B' getatr 'Width' winWidth 4 0** Centrar la ventana en la pantalla

C eval %setatr('FRA0000B':C 'FRA0000B':C 'Left')=(%DspWidth-winWidth)/2*

C eval %setatr('FRA0000B':C 'FRA0000B':C 'Bottom')=(%DspHeight-winHeight)/2** Obtener coordenadas iniciales del componente texto estático

C 'ST1' getatr 'Left' picX 4 0C 'ST1' getatr 'Bottom' picY 4 0** Obtener las dimensiones del componente texto estático

C 'ST1' getatr 'Height' picHeight 4 0C 'ST1' getatr 'Width' picWidth 4 0* * Calcular las coordenadas Y mínimas y máximas

C 'Start' getatr 'Height' startH 4 0C 'Start' getatr 'Bottom' startB 4 0C eval minY = startB + startHC eval maxY = winHeight - picHeight - 20*

Figura 28. Ejemplo de código en el que se utiliza el componente temporizador (Pieza 2 de 6)

170 Programación con VisualAge RPG

Page 189: c 0924494

* Calcular la coordenada X máximaC eval maxX = winWidth - picWidth*

C ENDACT********************************************************************** ** Ventana . : FRA0000B ** ** Componente : START ** ** Evento . . : PRESS ** ** Descripción: Iniciar el temporizador. ** ***********************************************************************

C START BEGACT PRESS FRA0000B*

C 'Timer1' setatr 1 'TimerMode'*

C ENDACT********************************************************************** ** Ventana . : FRA0000B ** ** Componente : STOP ** ** Evento . . : PRESS ** ** Descripción: Detener el temporizador. ** ***********************************************************************

C STOP BEGACT PRESS FRA0000B*

C 'Timer1' setatr 2 'TimerMode'*

C ENDACT

Figura 28. Ejemplo de código en el que se utiliza el componente temporizador (Pieza 3 de 6)

Capítulo 7. Utilización de componentes 171

Page 190: c 0924494

********************************************************************** ** Ventana . : FRA0000B ** ** Componente : CLOSE ** ** Evento . . : PRESS ** ** Descripción: Terminar el programa ** ***********************************************************************

C CLOSE BEGACT PRESS FRA0000B*

C eval *inlr = *on*

C ENDACT********************************************************************** ** Ventana . : FRA0000B ** ** Componente : TIMER1 ** ** Evento . . : TICK ** ** Descripción: Responder a los eventos tick del temporizador ** moviendo el componente texto estático de la ventana. ** ** Si el componente texto estático se mueve fuera del ** marco de la ventana, sus valores xChange e yChange ** se multiplican por -1 para invertir la dirección. ** **********************************************************************

Figura 28. Ejemplo de código en el que se utiliza el componente temporizador (Pieza 4 de 6)

172 Programación con VisualAge RPG

Page 191: c 0924494

*C TIMER1 BEGACT TICK FRA0000B** Calcular nuevas coordenadas de texto estático

C eval picX = picX + xChangeC eval picY = picY + yChange** Comprobar que el texto estático permanece dentro de la ventana

C select*

C picX whenlt 0C eval xChange = xChange * -1C eval picX = minX + xChange*

C picX whengt maxXC eval xChange = xChange * -1C eval picX = maxX + xChange*

C picY whenlt minYC eval yChange = yChange * -1C eval picY = minY + yChange*

C picY whengt maxYC eval yChange = yChange * -1C eval picY = maxY + yChange*

C endsl** Mover el texto estático a nuevas coordenadas

C 'ST1' setatr picX 'Left'C 'ST1' setatr picY 'Bottom'**

C ENDACT

Figura 28. Ejemplo de código en el que se utiliza el componente temporizador (Pieza 5 de 6)

********************************************************************** ** Ventana . : FRA0000B ** ** Componente : FRA0000B ** ** Evento . . : RESIZE ** ** Descripción: Obtener el tamaño de la ventana después de haber ** ajustado su tamaño para que el componente estático ** utilice toda la ventana. ** ***********************************************************************

C FRA0000B BEGACT RESIZE FRA0000B*

C eval maxY = %NewHeight - picHeight - 20C eval maxX = %NewWidth - picWidth*

C ENDACT

Figura 28. Ejemplo de código en el que se utiliza el componente temporizador (Pieza 6 de 6)

Capítulo 7. Utilización de componentes 173

Page 192: c 0924494

Barra de desplazamiento vertical

Utilice el componente barra de desplazamiento vertical para poder desplazarse porun panel de información de arriba abajo. La información puede ser una lista dearchivos, los registros de una base de datos, las columnas de un documento, yotros elementos. Puede utilizar el atributo Range para representar el número totalde los objetos por los que se efectuará el desplazamiento y el atributo PageSizepara determinar el número de objetos que pueden visualizarse en una página.

Atributos de componente

Bottom Enabled Focus Handle*Height Left NextLine NextPagePageSize ParentName PartName PartTypePosition PrevLine PrevPage RangeTop UserData Visible Width

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Create Destroy Scroll

174 Programación con VisualAge RPG

Page 193: c 0924494

Ventana

Las ventanas son el medio primordial que tiene el usuario de interactuar con elprograma. Las aplicaciones deben contener al menos una ventana.

Sólo puede añadir un componente al área de cliente de una ventana, con laexcepción de los componentes que son extensiones del marco de la ventana, comolas barras de menús, los menús emergentes y los subarchivos de mensajes. Eltamaño del componente que añada se ajusta automáticamente al área de cliente.

Si desea que una ventana contenga más de un componente, deberá añadirle uncomponente lienzo. El componente ventana con lienzo sirve también paraahorrarse un paso.

Nota: El componente ventana se encuentra en la sección Marcos del catálogo decomponentes, no en la paleta de componentes.

Para obtener información relacionada, consulte el apartado:v “Lienzo” en la página 53v “Ventana con lienzo” en la página 176

Atributos de componente

Bottom Center Enabled FileName*Focus* FontBold* FontItalic* FontName*FontSize* FontStrike* FontUnder* Handle*Height IconHandle* Label LeftMouseIcon* MouseShape* ParentName PartNamePartType PBRange PBSetPos PBStepPBStepSize Print ProgresBar RefreshSBLabel SBPosition SBStyle ShowTipsStatusBar Top UserData VisibleWidth WindowMode*

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Activate Close Create DeActivateDestroy LClickTray Moved RClickTrayReSize ShutDown

Capítulo 7. Utilización de componentes 175

|

Page 194: c 0924494

Ventana con lienzo

Las ventanas son el medio primordial que tiene el usuario final de interactuar conel programa. El lienzo, en un componente ventana con lienzo, le permite añadirvarios componentes a la ventana.

Puede colocar diversos componentes en el lienzo señalándolos y pulsando el botóndel ratón y cambiarlos de posición para crear una interfaz gráfica de usuario.También puede añadir componentes que sean extensiones del marco de la ventana,como barras de menús, menús emergentes y subarchivos de mensajes.

Si sólo precisa colocar un componente en el área de cliente de la ventana, nonecesita el componente ventana con lienzo: en lugar de éste, debe usar elcomponente ventana (que se encuentra en la sección Marcos del catálogo decomponentes). Sin lienzo, el tamaño del componente añadido se ajustaautomáticamente al área de cliente.

Para obtener información relacionada, consulte los apartados:v “Lienzo” en la página 53v “Ventana” en la página 175

Atributos de componente

Bottom Center Enabled FileName*Focus* FontBold* FontItalic* FontName*FontSize* FontStrike* FontUnder* Handle*Height IconHandle* Label LeftMouseIcon* MouseShape* ParentName PartNamePartType PBRange PBSetPos PBStepPBStepSize Print ProgresBar RefreshSBLabel SBPosition SBStyle ShowTipsStatusBar Top UserData VisibleWidth WindowMode*

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarse

Activate Close Create DeActivateDestroy LClickTray Moved RClickTrayReSize ShutDown

Visualización de una ventanaPor omisión, todas las ventanas se marcan con Visible y Open Immediatelycuando se crean en el Diseñador GUI.

Debe decidir qué ventana desea que el usuario vea en primer lugar. Esa ventana sedenomina ventana principal o primaria y debe establecer los atributos Visible y

176 Programación con VisualAge RPG

|

Page 195: c 0924494

Open Immediately de acuerdo a esto. Si no cambia los valores por omisión,aparecerán todas las ventanas cuando el usuario inicie la aplicación.

Establecimiento del atributo Open ImmediatelyEstablezca este atributo en tiempo de diseño si desea que la ventana se creecuando se inicie la aplicación. Al crear una ventana, ésta se carga en memoria:dado que se produce una actividad general asociada a esta carga, debe decidir quéventanas tienen que cargarse cuando se inicia la aplicación. (Es posible hacer quelas otras ventanas se carguen más adelante.) Puede utilizar el código de operaciónSHOWWIN para visualizar las ventanas que no se visualizan muy a menudo(como por ejemplo, la ventana que visualiza los derechos de propiedad intelectualde un producto ), en lugar de establecerlas para que se abran inmediatamente.

Nota: El atributo Open Immediately no controla si una ventana se visualizarealmente en la pantalla. Para visualizar una ventana, debe establecer en elprograma el valor 1 en el atributo Visible de dicha ventana, o debe marcarlacon Visible en el cuaderno propiedades.

Utilización del código de operación SHOWWINPuede cargar una ventana en el programa especificando el nombre de la ventanaen el Factor 2 del código de operación SHOWWIN. Este código de operación cargala ventana en la memoria.

Nota: La operación SHOWWIN no controla si una ventana se visualiza realmenteen la pantalla. Para visualizar una ventana, debe establecer en el programael valor 1 en el atributo Visible de dicha ventana, o debe marcarla conVisible en el cuaderno propiedades.

Los atributos de una ventana sólo pueden establecerse una vez que se ha cargado.Para cargar una ventana, seleccione el recuadro de selección Open Immediately enla página Inicio del cuaderno del componente o utilice el código de operaciónSHOWWIN en el programa.

Si una ventana está definida como Open Immediately y en el programa se emiteel código de operación SHOWWIN para esa ventana, se recibirá un error detiempo de ejecución indicando que la ventana ya se ha cargado. Puede evitar esteerror de tiempo de ejecución codificando un indicador de error en el código deoperación SHOWWIN y comprobando el indicador de error en el programa. Si elindicador está activado, la ventana ya está cargada y es preciso activar el atributoVisible. Así la ventana se visualizará y el error no se emitirá.

ReferenciaLos componentes de una ventana se crean cuando se crea la ventana. Porconsiguiente, si intenta hacer referencia a algún componente de una ventana queno se ha cargado o a un atributo de ventana antes de que se cree la ventana,obtendrá el mensaje Componente no encontrado.

Capítulo 7. Utilización de componentes 177

Page 196: c 0924494

Sugerencia

Si se visualiza una ventana y no puede pulsar el botón en la barra de títulode dicha ventana, utilice este método para moverla:1. Sitúe el cursor del ratón en un lugar de la parte visible de la ventana.2. Pulse y suelte el botón 1 del ratón.3. Pulse la combinación de teclas Alt-espacio. A continuación pulse M.4. Utilice las teclas con flecha para volver a situar la ventana.5. Cuando la ventana esté en la posición deseada, pulse Intro.

Cambio del tamaño de una ventanaPuede hacer dos cosas para crear la aplicación de manera que el usuario tenga unao más formas de cambiar el tamaño de una ventana:v En el Diseñador GUI, establezca que el borde de una ventana es Modificable.

Este valor permite al usuario seleccionar el borde de la ventana con el botón delratón y cambiar el tamaño de dicho borde mientras mantiene pulsado el botóndel ratón. En cuanto se suelta el botón del ratón, se señala el evento ReSize.

v Añada a la ventana los botones Maximizar y Minimizar. Esto permite al usuariocambiar el tamaño de la ventana seleccionando uno de estos botones.

Puede situar componentes en la ventana de tal manera que mantengan su posicióny tamaño relativos dentro de los límites de la ventana después de habermodificado el tamaño de ésta. Para ello, utilice el evento ReSize con los atributosde evento %NewHeight y %NewWidth.

En el ejemplo de codificación siguiente, un componente pulsador con la etiquetaPB1 está ubicado en la esquina superior derecha de una ventana. Al cambiar eltamaño de la ventana, la subrutina de acción ReSize calcula unos nuevos valoresde los atributos Left (Izquierda) y Bottom (Inferior) para asegurar que el pulsadorpermanezca dentro de los límites de la ventana.

178 Programación con VisualAge RPG

Page 197: c 0924494

********************************************************************** ** ID de programa : ReSize ** ** Descripción . : Programa de ejemplo que muestra cómo asegurar ** que los componentes permanecen en una ventana ** después de haber ajustado su tamaño. ** ** Se pone un pulsador en la esquina superior ** derecha de la ventana. Si se reduce el tamaño ** de la ventana, el pulsador dejará de ser ** visible, ya que todos los componentes mantienen ** su relación con la esquina inferior izquierda ** de la ventana. ** El evento RESIZE se utiliza para asegurar que ** el pulsador también mantiene su posición en ** relación con la esquina superior derecha de ** la ventana. ** ***********************************************************************

H** Declarar atributos de sistema de tamaño de pantalla

D%DspHeight S 4 0D%DspWidth S 4 0*

Figura 29. Comprobación de que los componentes se visualizan correctamente tras ajustar eltamaño de una ventana (Pieza 1 de 3)

Capítulo 7. Utilización de componentes 179

Page 198: c 0924494

* Declarar los atributos de evento %NewHeight y %NewWidth.* Contendrán la anchura y la altura de la ventana después de haber* ajustado su tamaño.

D%NewHeight S 4 0D%NewWidth S 4 0********************************************************************** ** Ventana . : FRA0000B ** ** Componente : FRA0000B ** ** Evento . . : RESIZE ** ** Descripción: Asegurar que el componente pulsador 'PB1' sigue ** visible. ** ***********************************************************************

C FRA0000B BEGACT RESIZE FRA0000B*

C %NewWidth sub HOffset NewLeft 4 0C %NewHeight sub VOffset NewBottom 4 0C 'PB1' setatr NewLeft 'Left'C 'PB1' setatr NewBottom 'Bottom'*

C ENDACT********************************************************************** ** Ventana . : FRA0000B ** ** Componente : PSB0000D ** ** Evento . . : PRESS ** ** Descripción: Terminar el programa ** ***********************************************************************

C PSB0000D BEGACT PRESS FRA0000B*

C move *on *inlr*

C ENDACT

Figura 29. Comprobación de que los componentes se visualizan correctamente tras ajustar eltamaño de una ventana (Pieza 2 de 3)

180 Programación con VisualAge RPG

Page 199: c 0924494

Establecimiento del focoDetermine con qué ventana desea que el usuario trabaje en primer lugar y utiliceel atributo Focus para poner el foco en esa ventana. Si no lo hace, VisualAge RPGdetermina qué ventana tendrá el foco cuando se carga la aplicación. Por omisión,la ventana que tiene el foco es la última ventana creada que tenga establecido elatributo Visible.

Lista de ventanasEn el cuaderno de propiedades para un componente ventana, puede indicar si laventana debe aparecer en la lista de ventanas. Esta lista aparece cuando pulsaControl+Alt+Delete en Windows NT/95/98. Por omisión, los componentes deventana no aparecen en la lista de ventanas. Debe establecer como mínimo laventana principal para que aparezca en la lista de ventanas. Puede utilizar la listade tareas para volver a visualizar la ventana.

********************************************************************** ** Ventana . : FRA0000B ** ** Componente : FRA0000B ** ** Evento . . : CREATE ** ** Descripción: Centrar la ventana en la pantalla. ** Obtener la coordenada actual del pulsador PB1 y su ** desplazamiento desde la esquina superior derecha ** de la ventana. ** ***********************************************************************

C FRA0000B BEGACT CREATE FRA0000B*

C 'FRA0000B' getatr 'Height' winHeight 4 0C 'FRA0000B' getatr 'Width' winWidth 4 0C %DspWidth sub winWidth diffWidth 4 0C %DspHeight sub winHeight diffHeight 4 0*

C eval %setatr('FRA0000B':C 'FRA0000B':C 'Left') = diffWidth / 2*

C eval %setatr('FRA0000B':C 'FRA0000B':C 'Bottom') = diffHeight / 2** Calcular los desplazamientos del componente pulsador 'PB1'* desde la esquina superior derecha de la ventana. Estos valores* se utilizan para mantener este desplazamiento si se ajusta el* tamaño de la ventana.

C 'PB1' getatr 'Left' PBLeft 4 0C 'PB1' getatr 'Bottom' PBBottom 4 0C 'FRA0000B' getatr 'Width' WinWidth 4 0C 'FRA0000B' getatr 'Height' WinHeight 4 0C WinWidth sub PBLeft HOffset 4 0C WinHeight sub PBBottom VOffset 4 0*

C ENDACT

Figura 29. Comprobación de que los componentes se visualizan correctamente tras ajustar eltamaño de una ventana (Pieza 3 de 3)

Capítulo 7. Utilización de componentes 181

Page 200: c 0924494

Terminación de un programaSi el usuario selecciona la opción Cerrar del menú del sistema en una ventana, elsistema operativo cierra la ventana pero no termina necesariamente el programa.Para evitar que esto suceda, puede realizar una de las acciones siguientes:v Seleccione el recuadro de selección Terminar al cerrar en la segunda página de

Estilo del cuaderno de propiedades de la ventana. Esto terminará el programacuando el usuario cierre la ventana.

v En la primera página de Estilo del cuaderno propiedades de la ventana,deseleccione el recuadro de selección Menú del sistema para que las ventanas secreen sin un Menú del sistema. (Por omisión, todas las ventanas se crean con unmenú del sistema.)

v Utilice el evento Close. Este evento se señala cuando el usuario seleccionaCerrar en el menú del sistema. En la subrutina de acción del evento Close,puede activar el indicador LR o solicitar al usuario que confirme que debecerrarse esta ventana y establecer el punto de retorno ENDACT de acuerdo aello. Por ejemplo, al establecer el valor de retorno en *NODEFAULT, la peticiónde cerrar se pasa por alto y la ventana no se cierra.

** Definir variables del recuadro de mensajes

Dstyle M button(*yesbutton: *nobutton)D style(*WARN)Dmsg M msgtext('Are sure you want to exit?')*********************************************************************** ** Ventana . : FRA0000B ** ** Componente : FRA0000B ** ** Evento . . : CLOSE ** ** Descripción: Manejar el evento Close desde el menú del sistema ** para ver si el usuario desea cerrar esta ventana. ** ***********************************************************************

C FRA0000B BEGACT CLOSE FRA0000B** Solicitud para cerrar

C msg dsply style rc 9 0** Si Yes, terminate program, se puede cerrar

C rc ifeq *YESBUTTONC move *on *inlrC movel '*DEFAULT 'return 12** Else no cierra esta ventana

C elseC movel '*NODEFAULT 'returnC endif*

C ENDACT return

182 Programación con VisualAge RPG

Page 201: c 0924494

Borrado de campos en una ventanaSi tiene varios campos de entrada en una ventana, puede utilizar el código deoperación CLEAR. Esto borrará todos los valores de los campos de entrada y losdevolverá a sus valores por omisión. Los campos numéricos se borran con ceros ylos campos de tipo carácter se borran con blancos.

Ejemplo de un componente ventanaEl componente ventana que se muestra más abajo tiene un menú del sistema, unbotón de minimizar y un botón de maximizar.

Capítulo 7. Utilización de componentes 183

Page 202: c 0924494

*Component

Este componente permite a los programadores acceder y utilizar atributos decomponente lógico y del sistema.

Un componente *component es la ″representación del componente″ delcomponente lógico. Para cada componente lógico se crea un componente*component; no se ve y no está en la paleta.

Atributos de componente

Active* Alarm AppData ButtonClipBoard CurrentDir Dialog DIRName*DlgOwner DoEvents* DspHeight DspWidthFileName HelpWindow LookNFeel* MsgDataMsgFile* MsgID MsgText NameOS Parent PartCount PartListPlatform PlugCmd* PlugDLL* PlugID*PlugRC* PlugResult* Printer* SelPrinter*ShData ShDataLen ShDataName ShDataPosShowMsgID SwitchTo* WrkStnName*

*Nota: Consulte la descripción del atributo si desea saber cuáles son lasrestricciones.

Eventos a los que puede aplicarseEste componente no tiene eventos asociados.

Utilización del componente *componentEl componente *component permite que los programadores accedan y utilicenatributos de componente lógico y de sistema. Un componente *component es la’representación de componente’ del componente lógico. Se crea automáticamenteun componente *component para cada componente lógico; no es visible y no seencuentra en la paleta de componentes.

Visualizar un diálogo Abrir/Guardar como de ArchivoLos atributos Button, FileName, Dialog y DlgOwner del componente *componentse utilizan para visualizar el diálogo común de Windows Abrir o Guardar como deArchivo. El atributo de diálogo determina qué tipo de diálogo se visualizará.Establézcalo en 1 para visualizar un diálogo Abrir o en 2 para visualizar undiálogo Guardar como. DlgOwner designa qué componente es el ’propietario’ deldiálogo. Una vez establecido el atributo, el propietario ’depende’ del diálogo. Estosignifica que el propietario ni puede responder a los eventos hasta que el diálogono sea rechazado. Al establecer el atributo FileName se visualiza el diálogo abrirde archivo. Para determinar qué botón ha utilizado el usuario para rechazar eldiálogo, recupere el valor del atributo Button.

En el siguiente ejemplo, se visualiza un diálogo Abrir de Archivo. Fíjese que elatributo FileName puede establecerse para visualizar únicamente archivos concierta extensión:

184 Programación con VisualAge RPG

Page 203: c 0924494

Seleccionar una impresoraSi la aplicación imprime en una impresora conectada a la estación de trabajo,puede utilizar los atributos SelPrinter y Printer para permitir que el usuarioseleccione a qué impresora enviará la salida. Si establece el atributo SelPrinter en 1verá el diálogo Imprimir de Windows que se visualizará. Cuando el usuarioselecciona una impresora desde ese diálogo, la salida impresa de la aplicación seenviará a dicha impresora.

Utilización de conectoresLos atributos PlugDLL, PlugID, PlugCmd, PlugRC y PlugResult le darán laposibilidad de ampliar la funcionalidad del Diseñador GUI. Proporcione lafuncionalidad complementaria a un programa que haya desarrollado. Una vez laaplicación esté registrada en el Preparador GUI mediante el menú Proveedor, laaplicación puede interactuar con el Diseñador GUI. Consulte el capítulo 20 paraconocer más detalles sobre cómo crear conectores.

Consultar los componentes de un componente lógicoLos atributos Parent, PartCount y PartList pueden utilizarse durante la ejecuciónpara consultar los nombres de los componentes de un componente lógico. Porejemplo, podría utilizar estos atributos para ajustar el tamaño de los componentesy volver a situarlos en una ventana si el tamaño de la ventana ha sido ajustado denuevo.

** Visualizar el diálogo Abrir de Archivo

C '*Component' Setatr 1 'Dialog'** Esta ventana es el propietario

C '*Component' Setatr 'Main Main' 'DlgOwner'** Mostrar sólo los archivos .DAT

C '*Component' Setatr '*.DAT' 'Filename'** Pulsar el botón

C '*Component' Getatr 'Button' Button 1 0** Utilizar el pulsador Aceptar

C If Button = 1** Usuario cancelado

C Else*

C EndIf

Figura 30. Visualizar un diálogo Abrir de Archivo

Capítulo 7. Utilización de componentes 185

Page 204: c 0924494

186 Programación con VisualAge RPG

Page 205: c 0924494

Parte 3. Cómo trabajar con datos AS/400“Capítulo 8. Conectividad con AS/400” en la página 189

Describe cómo configurar una conexión entre la aplicación y un AS/400.

“Capítulo 9. Reutilizar aplicaciones AS/400” en la página 201Describe cómo importar archivos de pantalla existentes, ayuda de UIM yfuente RPG desde aplicaciones AS/400 existentes.

© Copyright IBM Corp. 1994, 2000 187

Page 206: c 0924494

188 Programación con VisualAge RPG

Page 207: c 0924494

Capítulo 8. Conectividad con AS/400

Si se utiliza un servidor AS/400 mientras se está desarrollando la aplicación (porejemplo, importando archivos de pantalla de AS/400) o mientras se está ejecutandola aplicación (por ejemplo, al acceder a archivos de base de datos de AS/400 paraE/S), debe definir la información de AS/400 utilizada por la aplicación. Estainformación se almacena por separado de la aplicación, de manera que puedaactualizarse sin cambiar la propia aplicación.

En esta sección se tratan los siguientes temas:v Definición de la información de AS/400v Configuración de un servidor AS/400 en tiempo de diseño y en tiempo de

ejecuciónv Utilización de áreas de datosv Utilización de archivos de base de datos AS/400v Consideraciones sobre E/S de base de datos

Definición de la información de AS/400Durante el desarrollo de la aplicación, puede utilizar el cuaderno de propiedadesDefinir información de AS/400 para definir pseudónimos (nombres de alteracióntemporal) para la siguiente información de AS/400:v Servidoresv Archivosv Programasv Áreas de datosv Nivel de bloqueo

Una vez que haya desarrollado una aplicación y esté listo para instalarla en laestación de trabajo del usuario, tiene que asegurarse de que:v Para las comunicaciones SNA, se haya configurado lo siguiente:

Debe definirse un direccionador mediante Client Access. Este nombre dedireccionador también se utiliza como Nombre de ubicación remota.

v Para las comunicaciones TCP/IP, se haya configurado lo siguiente:Utilice el nombre de sistema principal definido para el AS/400 como Nombre deubicación remota.

También puede consultar en el manual Iniciación a VisualAge RPG y CODE/400, lospasos necesarios para definir la información de AS/400.

Consideraciones sobre el cuadernoSi las páginas del cuaderno de propiedades Definir información de AS/400 nocontienen el nombre de alteración temporal del programa, el área de datos o elarchivo de base de datos, ocurre lo siguiente:1. Se utiliza el nombre del programa, área de datos o archivo de base de datos del

programa.2. Si el nombre del programa, área de datos o archivo de base de datos está

cualificado por biblioteca en el programa, se utiliza esta biblioteca.3. Si el nombre del programa o el archivo de base de datos no está cualificado por

biblioteca en el programa, se busca en la lista de bibliotecas (*LIBL) en elservidor AS/400.

4. Se utiliza el primer servidor listado en la página de servidores.

© Copyright IBM Corp. 1994, 2000 189

Page 208: c 0924494

Nota: El primer servidor listado en la página de servidores del cuaderno Definirinformación de AS/400 se conoce como servidor por omisión. Se requierepor lo menos un servidor por cada programa que utilice un servidorAS/400.

Configuración de un servidorDebe configurar un servidor cuando esté desarrollando la aplicación, de maneraque pueda acceder al servidor mientras se edita, compila y depura la aplicación.Cuando empaquete y distribuya la aplicación a otras estaciones de trabajo, tambiéntendrá que configurar un servidor si la aplicación en ejecución accede a unservidor distinto del utilizado durante el tiempo de diseño.

Siempre que configure un servidor, asegúrese de que la lista de bibliotecas deltrabajo de servicio contiene el recurso remoto con el que desea trabajar.

Establecimiento de un servidor en tiempo de diseñoSi tiene que utilizar un servidor mientras está desarrollando la aplicación, debedefinir la información del servidor en la ventana Definir conexión a servidores y enel cuaderno Definir información de AS/400. Consulte Iniciación a VisualAge RPG yCODE/400 si desea más información.

También debe definir una descripción de trabajo de AS/400 para configurar la listade bibliotecas. Puede asociar una lista de bibliotecas con una descripción de trabajoen el servidor AS/400. Luego, esta descripción de trabajo puede asociarse a unperfil de usuario. Utilice el ID de usuario de este perfil de usuario cuando elVisualAge RPG le solicite que inicie una sesión en un servidor. El trabajo deservicio AS/400 contiene la lista de bibliotecas correcta.

Establecimiento de un servidor en tiempo de ejecuciónSi tiene que acceder a un servidor mientras está ejecutando la aplicación, debeverificar que la información de AS/400 indique el servidor correcto. Utilice elprograma de utilidad Definir información de AS/400 para invocar el cuadernoDefinir información de AS/400.

También debe configurar la lista de bibliotecas cambiando la descripción de trabajoo utilizando los mandatos CL QCMDDDM o QCMDEXC.

Definición de una descripción de trabajo para configurar unalista de bibliotecasPuede asociar una lista de bibliotecas con una descripción de trabajo en el servidorAS/400. Luego, esta descripción de trabajo puede asociarse a un perfil de usuario.Utilice el ID de usuario de este perfil de usuario cuando el VisualAge RPG lesolicite que inicie una sesión en un servidor. El trabajo de servicio AS/400 contienela lista de bibliotecas correcta.

Cambio de la lista de bibliotecasSi un programa VisualAge RPG llama a mandatos CL de AS/400:v Especifique una operación CALL a QCMDDDM si el mandato CL emite

mandatos para archivos AS/400.v Especifique CALL a QCMDEXC si el mandato CL emite mandatos a programas

AS/400 o a áreas de datos AS/400.

Pueden emitirse mandatos CL para ejecutarlos en el trabajo de servicio DDMAS/400 mediante el código de operación CALL. Debe llamarse a un programa

190 Programación con VisualAge RPG

Page 209: c 0924494

especial para que se ejecute el mandato CL en el trabajo de servicio DDM AS/400.El programa especial es QCMDDDM. Esta interfaz es la misma que la interfaz parallamar a QCMDEXC. La diferencia entre QCMDEXC y QCMDDDM es queQCMDEXC se ejecuta en un trabajo AS/400 distinto que se utiliza para darservicio a peticiones de llamada remota y peticiones de área de datos.

Puede utilizarse QCMDDDM para cambiar la lista de bibliotecas del trabajo deservicio DDM para asegurar que la biblioteca que contenga los archivos de base dedatos AS/400 esté presente en la lista de bibliotecas del trabajo DDM.

Utilización de áreas de datosAntes de que la aplicación pueda utilizar áreas de datos, debe configurar elservidor.

Si la aplicación accede a un área de datos de AS/400, el nombre de ésta puede serel nombre del área de datos de AS/400 o un nombre de alteración temporal. Puededefinir el nombre de alteración temporal en el Diseñador GUI utilizando la páginaÁrea de datos del cuaderno Definir información de AS/400.

Vea “Consideraciones sobre el cuaderno” en la página 189 si la página delcuaderno no contiene un nombre de alteración temporal para el área de datos.

La Tabla 5 y la Figura 31 en la página 192 muestran cómo acceder a un área dedatos utilizando un nombre de alteración temporal.

Tabla 5. Entrar esta información en la página Área de datos del cuaderno Definir informaciónde AS/400

Nombre de alteración temporal de área dedatos:

DTAARA (debe entrarse en mayúsculas)

Nombre de área de datos remota: REMDTAARA

Pseudónimo del servidor: SERVER01

Asegúrese de que se ha inicializado el área de datos antes de intentar utilizarla. Seemite una excepción de tiempo de ejecución si un área de datos en el servidor nocontiene un valor decimal empaquetado válido al intentar recuperarlo en unaestructura de datos de área de datos con un subcampo decimal empaquetado enun programa VisualAge RPG.

Capítulo 8. Conectividad con AS/400 191

Page 210: c 0924494

Utilización de archivos de base de datos de AS/400Antes de que la aplicación pueda acceder a archivos de base de datos de AS/400,debe configurar el servidor.

Los nombres de archivos DISK remotos utilizados en los programas VisualAgeRPG pueden ser un nombre de archivo AS/400 o un nombre pseudónimo dearchivo. Puede definir un nombre pseudónimo de archivo mediante la páginaArchivo del cuaderno Definir información de AS/400. Vea “Consideraciones sobreel cuaderno” en la página 189 para obtener información acerca de lo que sucede sila página de cuaderno no contiene un pseudónimo de archivo para el archivoAS/400.

Las peticiones de apertura emitidas por la aplicación VisualAge RPG pasan poralto las alteraciones temporales de archivo de base de datos de AS/400 emitidas enel trabajo DDM de AS/400 remoto. Las peticiones de apertura efectuadas porprogramas AS/400 que se ejecutan en el trabajo de servicio DDM pueden optarpor pasar por alto o aplicar las alteraciones temporales de archivo.

El VisualAge RPG soporta la alteración temporal de nombre de biblioteca, nombrede archivo y nombre de miembro de AS/400, utilizando la página Archivo delcuaderno Definir información de AS/400.

El cuaderno Definir información de AS/400 se utiliza cuando está construyéndosela aplicación y mientras ésta está ejecutándose. En el tiempo de construcción, lapágina Archivo se utiliza durante las extracciones de archivos para buscar lasdescripciones externas de los archivos. También se utiliza para una estructura dedatos descrita externamente cuando así se especifique en una especificación dedefinición.

********************************************************************** ** Id. de programa: dtaaraex.vpg ** ** Descripción . : Segmento de código para obtener el contenido de ** un área de datos de AS/400. ***********************************************************************

D dtaara S 6P 0 DTAARA********************************************************************** ** Ventana. . : WIN1 ** ** Componente : PSB0000C ** ** Evento . . : PRESS ** ** Descripción: Obtener el contenido del área de datos de AS/400. ***********************************************************************

C PSB0000C BEGACT PRESS WIN1C IN dtaaraC ENDACT

Figura 31. Acceso a un área de datos de AS/400

192 Programación con VisualAge RPG

Page 211: c 0924494

En el tiempo de ejecución de la aplicación, la página Archivo se utiliza paralocalizar los archivos de base de datos de AS/400 remotos que están utilizándoserealmente. El nombre pseudónimo de archivo utilizado en el programa VisualAgeRPG se usa para buscar una entrada adecuada en la página Archivo.

Si no existe ninguna entrada en la página Archivo, se utiliza la lista de bibliotecasdel primer servidor definido en la página del servidor para buscar un archivo conel mismo nombre que el archivo del programa VisualAge RPG.

Mantener el nombre de archivo real separado del nombre de archivo utilizado enel programa VisualAge RPG le permite cambiar el destino del archivo real. Puededirigirlo a un archivo diferente en el mismo sistema AS/400 o en un sistemaAS/400 diferente sin modificar el programa VisualAge RPG.

La Figura 32 en la página 194 contiene un ejemplo que muestra:v La asociación de nombres de archivo con entradas de archivo en la página

Archivo en el cuaderno Definir información de AS/400.v Nombres de componente coincidentes con campos.

Nota: La información sobre NAME (NOMBRE) y ADDRESS (DIRECCIÓN) debeentrarse en la ventana de la aplicación. La información se entra en la basede datos de AS/400 cuando se acciona el pulsador Aceptar.

Capítulo 8. Conectividad con AS/400 193

Page 212: c 0924494

********************************************************************** ** Id. de programa: ioex.vpg ** ** Descripción . : Crear registros con datos de la ventana. ** ** Archivos . . . : FILE1 ** ***********************************************************************

FFILE1 UF A E DISK REMOTE USROPN********************************************************************** ** Ventana. . : WIN1 ** ** Componente : *INZSR ** ** Evento . . : Rutina de inicialización ** ** Descripción: Abrir archivo de base de datos (FILE1). ** ***********************************************************************

C *INZSR BEGSRC OPEN FILE1C ENDSR********************************************************************** ** Ventana. . : WIN1 ** ** Componente : PSB0000D ** ** Evento . . : PRESS ** ** Descripción: Fin de creación de registros. Fin de aplicación. ** ***********************************************************************

C PSB0000D BEGACT PRESS WIN1C SETON LRC ENDACT

Figura 32. Ejemplo de archivo de base de datos (Pieza 1 de 2)

194 Programación con VisualAge RPG

Page 213: c 0924494

FILE1 en la especificación de archivo se utiliza como pseudónimo de archivo, yaque existe una entrada en la página Archivo del cuaderno Definir información deAS/400 asociado.

Durante la apertura de archivo se utiliza el primer miembro de FILE1 de labiblioteca LIB1 en el servidor TORAS180. FILE1 en el nombre remoto no tiene quecoincidir con el nombre de alteración temporal en la entrada de archivo. El nombrede alteración temporal representa un enlace entre la entrada de archivo en lapágina Archivo y el nombre de archivo utilizado en el programa VisualAge RPG.

Los nombres de componente de los dos campos de entrada son NAME yADDRESS. VisualAge RPG crea campos con los mismos nombres y los mismosatributos. En este ejemplo, NAME y ADDRESS son campos de 20 caracteres. Elarchivo de base de datos de AS/400 también contiene dos campos denominadosNAME y ADDRESS, ambos de 20 caracteres. A continuación verá las DDScorrespondientes a estos campos:

R RECORD100A NAME 20AA ADDRESS 20A

Cuando coinciden los nombres de campo con sus atributos, sólo se crea un campo.En este ejemplo se leen los datos de la ventana.

Cuando se ejecuta este READ, los datos se mueven automáticamente de la pantallaa los dos campos NAME y ADDRESS. Dado que los datos están ahora en loscampos adecuados, estos datos pueden escribirse directamente en la base de datosde AS/400 sin ningún otro movimiento de campo.

********************************************************************** ** Ventana. . : WIN1 ** ** Componente : PSB0000C ** ** Evento . . : PRESS ** ** Descripción: Leer información de campo de la pantalla y añadir ** registro a archivo de base de datos de AS/400. ** ** ***********************************************************************

C PSB0000C BEGACT PRESS WIN1C READ 'WIN1'C WRITE FORMAT1C ENDACT

Figura 32. Ejemplo de archivo de base de datos (Pieza 2 de 2)

C* N01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEq..

C READ 'WIN1'

C* N01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEq..

C WRITE FORMAT1

Capítulo 8. Conectividad con AS/400 195

Page 214: c 0924494

En este ejemplo, los datos de los dos campos NAME y ADDRESS se mueven alalmacenamiento intermedio de salida antes de emitir el mandato de escribir a labase de datos de AS/400.

Comprobación de nivelVisualAge RPG soporta la comprobación de nivel entre un programa VisualAgeRPG y los archivos de base de datos de AS/400 que están utilizándose.

El compilador siempre proporciona la información que la comprobación de nivelnecesita. La comprobación de nivel se produce sobre la base de formato de registrocuando el archivo se abre, a menos que se especifique LVLCHK(*NO) al crear ocambiar el archivo de base de datos de AS/400.

Nota: Si se produce una comprobación de nivel, se trata como un error de E/S. Sidesea más información, consulte la publicación VisualAge RPG Manual deconsulta del lenguaje.

Bloqueo de archivos de base de datos de AS/400El sistema OS/400 permite que se coloque un estado de bloqueo (exclusivo,exclusivo con permiso para leer, compartido para actualizar, compartido sinactualizar, o compartido para leer) en un archivo utilizado durante la ejecución deun trabajo. Los programas que están dentro de un trabajo no se ven afectados porlos estados de bloqueo de los archivos. Un estado de bloqueo de archivo se aplicasólo cuando un programa de otro trabajo intenta utilizar el archivo de maneraconcurrente. El estado de bloqueo de archivo puede asignarse con el mandato CLALCOBJ (Asignar Objeto). Si desea obtener más información acerca de laasignación de recursos y los estados de bloqueo, puede consultar la sección CL andAPIs de la categoría Programming del Information Center situado en el sitio Web -http://publib.boulder.ibm.com/pubs/html/as400/infocenter.htm.

El sistema OS/400 coloca los siguientes estados de bloqueo en archivos de base dedatos cuando abre los archivos:v Abierto para INPUT: Estado de bloqueo Compartido para leerv Abierto para UPDATE: Estado de bloqueo Compartido para actualizarv Abierto para ADD: Estado de bloqueo Compartido para actualizarv Abierto para OUTPUT: Estado de bloqueo Compartido para actualizar

Alteración temporal de archivos de base de datosPara alterar temporalmente el nombre de archivo o biblioteca de un archivo debase de datos AS/400, utilice el mandato QCMDDDM tal como se indica en elsiguiente ejemplo:

D QCMDDDM C 'QCMDDDM' Linkage(*Server)C OvrMenufl BEGSR

C Eval QCMDDDM_Parm1 = 'OVRDBF FILE(MENUFL)' +C

' TOFILE(SYSLIBT/MENUFL)' +C

' MBR(' + MemberName + ')' +C

' OVRSCOPE(*JOB)' +C

' OPNSCOPE(*JOB)'C Exsr CallExecDDM

C ENDSR

196 Programación con VisualAge RPG

Page 215: c 0924494

C CallExecDDM BEGSR

C EVAL QCMDDDM_Parm2 = %LEN(QCMDDDM_Parm1)C Call QCMDDDMC Parm QCMDDDM_Parm1C Parm QCMDDDM_Parm2

C ENDSR

Consideraciones de E/S de base de datos de AS/400En general, todas las operaciones de E/S de base de datos VisualAge RPGdisponibles en el lenguaje ILE RPG/400 también lo están en el lenguaje VisualAgeRPG y son equivalentes semánticamente. Consulte el manual VisualAge RPGManual de consulta del lenguaje para obtener más información, incluyendo loscódigos de operación que soportan el acceso local, el acceso remoto o ambos.

Utilización de bloques de registros para mejorar elrendimiento

Si la aplicación lee datos de un AS/400, puede mejorar el rendimiento de laaplicación mediante bloques de registros. Crear bloques de registros significa quelas operaciones de E/S del archivo se realizan en varios registros secuenciales (enbloques de registros) en lugar de hacerse de registro en registro.

VisualAge RPG ofrece el bloqueo de registros por omisión si se cumple cualquierade las condiciones siguientes:v El archivo es de sólo salida y únicamente contiene un formato de registro.v El archivo es un archivo combinado.v El archivo es de sólo entrada, únicamente contiene un formato de registro y sólo

utiliza los códigos de operación OPEN, CLOSE, FEOD y READ.v La palabra clave RECNO no está especificada en la especificación de descripción

de archivo.

Además, puede realizar bloqueos de registros explícitos en archivos que cumplenlos criterios siguientes:v La entrada Adición de archivo (posición 20) está en blanco.v La palabra clave RECNO no se utiliza en el archivo.v El archivo sólo tiene un formato de registro.v En el archivo se utilizan los códigos de operación CHAIN, SETLL o SETGT.v Los códigos de operación READE, READP o READPE no se utilizan en el

archivo.

Si un archivo cumple los criterios antedichos, puede habilitar la creación debloques de registros actualizando el programa con BLOCK(*YES) en la descripciónde archivo y volviendo a compilar el programa. La Figura 33 en la página 198muestra un ejemplo que utiliza la opción de palabra clave BLOCK.

Capítulo 8. Conectividad con AS/400 197

Page 216: c 0924494

Si utiliza BLOCK(*NO) en una descripción de archivo y vuelve a compilar elprograma, no se crearán bloques de registros, ni siquiera los bloques de registrospor omisión que VisualAge RPG soporta.

Servidores utilizados en el AS/400Si utiliza TCP/IP, los servidores Central optimizado y Mandato remoto deben estaractivados. Utilice el mandato STRHOSTSVR para iniciar estos servidores. Consultela publicación Client Access Express for Windows Host Servers.

Estos servidores son necesarios para desarrollar las aplicaciones. Además, alejecutar las aplicaciones, el servidor DDM de TCP/IP debe estar activo. Utilice elmandato STRTCPSRV para iniciar el servidor.

Utilización del archivo de seguridad para los appletsCuando una aplicación VARPG necesita un recurso del AS/400 como, por ejemplo,un archivo de base de datos, se requiere un ID de usuario y una contraseñaválidos para conectarse al sistema AS/400. En VARPG, el ID de usuario y lacontraseña se almacenan en un archivo de seguridad ubicado en la estación detrabajo cliente. No obstante, por omisión, los applets no pueden acceder a ningúnarchivo de la estación de trabajo cliente. En consecuencia, el sistema solicitará alusuario un ID de usuario y una contraseña cada vez que se ejecute un applet. Sidesea utilizar el archivo de seguridad al ejecutar applets y evitar esta solicitud,deberá dar a cada applet permiso para leer el archivo de seguridad. Puede otorgarestos permisos utilizando el programa de utilidad PolicyTool que forma parte delJ2SDK de Sun Microsystem. En la sección relativa a la documentación de laherramienta de la documentación del J2SDK 1.2 encontrará más información sobrecómo utilizar PolicyTool.

Nota: El procedimiento que aquí se describe sólo funciona para los clientesWindows.

1. Cree el archivo de seguridad en la estación de trabajo cliente.Si aún no lo ha hecho, instale la unidad de ejecución de VARPG en la estaciónde trabajo cliente. En el menú Inicio, elija Programas>VisualAge para RPG -Tiempo de ejecución>Definir conexión a servidores. Aparecerá el diálogoDefinir conexión a servidores. Añada el ID de usuario y la contraseña de unsistema AS/400 determinado para almacenarlos en el archivo de seguridad.

2. Cree los permisos necesarios.Los permisos son necesarios para que la VM Java pueda leer el archivo deseguridad. Para crear los permisos, realice las siguientes acciones:a. En un indicador del DOS, escriba PolicyTool y pulse Intro. Aparecerá el

diálogo Policy Tool.Si es la primera vez que utiliza PolicyTool, también se mostrará un mensajeindicando que no puede encontrarse el archivo de políticas en un cierto

FFILE1 IF E K DISK BLOCK(*YES)F REMOTE

...C FLD2 SETLL REC1

...C READ REC1 10

Figura 33. Ejemplo de utilización de la opción de palabra clave BLOCK

198 Programación con VisualAge RPG

Page 217: c 0924494

directorio. Anote el nombre y el directorio del archivo de políticas queaparece en el mensaje. Ésta será la ubicación donde guardará el archivo depolíticas en un paso posterior.

b. En el diálogo Policy Tool, pulse el botón Add Policy Entry. Aparecerá eldiálogo Policy Entry. En el campo de entrada CodeBase, escriba:"http://xxxx/-",

donde xxxx es el URL y el directorio que contiene el applet que debe recibirpermisos para el archivo de seguridad.

c. Pulse el botón Add Permission. Complete el diálogo Permissions tal comose indica a continuación:v En el recuadro combinado Permissions, elija RuntimePermission.v En el recuadro combinado Target, elija loadLibrary.<nombre biblioteca>.v En el campo de entrada situado inmediatamente a la derecha del

recuadro combinado Target, cambie loadLibrary.<nombre biblioteca>por loadLibrary.fvdcjava.

v Pulse OK para regresar al diálogo Policy Entry.d. En el diálogo Policy Entry, vuelva a pulsar el botón Add Permission.

Complete el diálogo Permissions tal como se indica a continuación:v En el recuadro combinado Permissions, elija FilePermission.v En el campo de entrada situado inmediatamente a la derecha del

recuadro combinado Target, escriba el nombre del archivo de seguridad.Este archivo se encuentra ubicado en el subdirectorio ibmcom deldirectorio de Windows. Por ejemplo:c:\windows\ibmcom\fvdcsec.txt

donde el directorio de Windows es c:\windows.v En el recuadro combinado desplegable Actions, elija read.v Pulse OK para regresar al diálogo Policy Entry.v Pulse Done para regresar al diálogo Policy Tool.

e. En el diálogo Policy Tool, elija File y, a continuación, Save as en el menú.Guarde el archivo de políticas que acaba de crear en el nombre de archivo ydirectorio que anotó en el paso 2a en la página 198. Ahora elija File y, acontinuación, Exit para salir de PolicyTool.Si todavía se le solicita el ID de usuario y la contraseña, vuelva a utilizarPolicyTool para verificar que ha especificado correctamente todos losparámetros.

Capítulo 8. Conectividad con AS/400 199

Page 218: c 0924494

200 Programación con VisualAge RPG

Page 219: c 0924494

Capítulo 9. Reutilizar aplicaciones AS/400

Al desarrollar una aplicación VisualAge RPG, tal vez desee reutilizar otraaplicación AS/400 existente o diversos fragmentos de esta aplicación. Esta seccióndescribe algunas cosas que debe tener en cuenta al reutilizar aplicaciones AS/400.

Situación de reutilizaciónPuede utilizar VisualAge RPG para modificar aplicaciones que se ejecutan en elAS/400 de manera que se ejecuten en una PWS, acceder a datos en el sistemaprincipal y tener una interfaz gráfica de usuario. Esta sección proporciona unavisión general de los pasos relacionados en el proceso.

Importación de archivos de pantalla: El programa de utilidad de Importaciónconvierte los archivos de pantalla AS/400 existentes en una interfaz gráfica deusuario en una PWS. Después de importar un archivo de pantalla, los formatos deregistro se convierten en componentes definidos por usuario y se almacenan en lapágina Importado del catálogo de componentes. Puede mover los componentes ala paleta de componentes mientras trabaja en la aplicación, y luego almacenarlosen el catálogo de componentes cuando termine de trabajar en la aplicación, hastaque vuelva a necesitarlos.

Por ejemplo, si importa la pantalla 5250 que se muestra en la Figura 34 en lapágina 202 obtendrá como resultado la GUI que se muestra en la Figura 35 en lapágina 203. Los registros se convierten en un grupo de componentes, los campos seconvierten en componentes campo de entrada y las constantes se convierten encomponentes texto estático. Todas las teclas de mandato se convierten encomponentes pulsador y las etiquetas de pulsador reflejan la palabra clave de teclade mandato original.

© Copyright IBM Corp. 1994, 2000 201

Page 220: c 0924494

OOO OO OOOO OOOOOOOOOOOOOOOOOOOOOOOOOOOOOO Status: OOOOOOO

Purchase Order Header Maintenance P.O. Number: 666666-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.

Vendor Number: 99999 OOOOOOOOOOOOOOOOOOOOOOOOO OOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOO 66666666-666-6666OOOOOOOOOOOOOOOOO OOOOOOO

OOOOOOOOOOOOOOOOOOOOOOOOOOOOOO

Ship to: 9999 OOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOOO

Print : B (Y,N)Ship Via: BBBBBBBBBB Date Entered: OOO OO OOOOF.O.B.: BBBBBBBBBBBBBBB Date Revised: OOO OO OOOO

Terms Code : BBBB OOOOOOOOOOOOOOO OOO OO OOOOPassword : Originator : OOOOOOOOOOOOOOO

Prep./Collect/Chg : B (P,C,X)Confirm./Orig. : B (C,O)

Warehouse: BB OOOOOOOOOOOOOOOOOOOOOOOOOOOOOORequested by: BBBBBBBBBBBBBBB Work Order #: 9999999

-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.-.Cmd1 Exit Cmd3 PO Notes Cmd4 Lookup Cmd5 Material Status Cmd9 Vendor Maint.Cmd11 Delete Cmd15 Vendor Notes Cmd16 Vendor Quotes

Figura 34. Pantalla 5250 de ejemplo de una aplicación Purchase Order

202 Programación con VisualAge RPG

Page 221: c 0924494

Nota: Los nuevos componentes conservan los nombres de campo originales, peroel usuario puede redenominarlos si lo desea. Conservar el mismo nombre decampo mejora la productividad al manipular la lógica de programa para unanueva utilización.

Tal vez desee personalizar los componentes importados para aprovechar los temasde diseño básico analizados en el “Capítulo 2. Planificación de la aplicación” en lapágina 19.

Personalización de la GUI:

Figura 35. Resultado de importar la pantalla Purchase Order

Capítulo 9. Reutilizar aplicaciones AS/400 203

Page 222: c 0924494

La Figura 36 muestra qué aspecto podría tener la ventana importada si efectúa lossiguientes cambios en la interfaz:v Sustituya las teclas de mandato con una barra de menús y los elementos de

menú asociados. Por ejemplo, un menú Vendor (Proveedor) contiene accionesque originalmente se convirtieron en pulsadores. Esto da a los usuarios accesolibre a las acciones realizadas con frecuencia y lanza ventanas relacionadas.

v Agrupe la información relacionada mediante componentes recuadro de grupopara proporcionar una guía visual a los usuarios. Por ejemplo, un recuadro degrupo con la etiqueta Shipment Information (Información de envío) contienecampos de entrada que pertenecen a la información de envío.

v Utilice los botones de selección agrupados para obtener información querequiera que un usuario seleccione entre varias opciones conocidas. Por ejemplo,sólo son posibles tres métodos de pago (prepago, cobro y cargo); porconsiguiente, los usuarios sólo tienen que seleccionar un botón de selección paraindicar el método que está utilizándose. Los botones de selección están en unrecuadro de grupo con la etiqueta Payment (Pago).

Estos cambios aprovechan las posibilidades gráficas que ofrece VisualAge RPG.

Reutilización de la ayuda en línea: Cuando vuelva a utilizar una aplicación, talvez también desee usar de nuevo la ayuda del User Interface Manager (UIM)existente. Tendrá que modificarla un poco para reflejar el aspecto de la nueva GUI;no obstante, podría ahorrarle el trabajo necesario para crear ayudas desde cero.

Puede personalizar la ayuda de UIM convertida y añadir nuevos tipos de ayudautilizando IPF (Recurso de Presentación de Información). Puede escribir ayudapara cada ventana y ayuda según contexto para cada componente, y puede enlazarla información de ayuda creando enlaces de hipertexto en el fuente de ayuda. Vea

Figura 36. GUI personalizada para la aplicación Purchase Order

204 Programación con VisualAge RPG

Page 223: c 0924494

“Reutilizar ayuda UIM” en la página 212 y “Capítulo 13. Consejos para crear ayudaen línea con IPF” en la página 235 para obtener más información.

Cómo escribir lógica de programa: Puede reutilizar la lógica escrita en RPG IVporque el compilador está basado en ese lenguaje. Basta con que corte y pegue elcódigo existente para reutilizarlo.

También tiene que escribir lógica de programa adicional utilizando laprogramación dirigida por eventos. Para cada evento asociado a un componente,hay una subrutina de acción que describe cómo el programa responde a un evento.Los códigos de operación de procedimiento para el control de programa no sonnecesarios; el control del programa está implícito. Algunos códigos de operación deVisualAge RPG exclusivos de las aplicaciones VisualAge RPG son:

BEGACTEmpieza una subrutina de acción

ENDACTFinaliza una subrutina de acción

SETATREstablece el valor de un atributo de componente

GETATRRecupera el valor de un atributo de componente

SHOWWINVisualiza una ventana

CLSWINCierra una ventana

La Figura 37 en la página 206 contiene una subrutina de acción de una aplicaciónde ejemplo de pedidos de compra. Cuando se llama a SHOWWIN desde unaventana determinada para visualizar la ventana PUR570R2, se codifica unasubrutina de acción para el evento Create con el fin de preparar la ventana para lasiguiente acción de un usuario.

Si es un pedido de compra nuevo (#PONUM = 0), los elementos de menú change,delete, print y fax se establecen para no responder al evento MENUSELECT. Paracada uno de los elementos de menú, se utiliza la función %setatr para establecer elatributo enabled en 0. El código de operación BEGACT indica el inicio de lasubrutina de acción y ENDACT indica su final.

Capítulo 9. Reutilizar aplicaciones AS/400 205

Page 224: c 0924494

Conexión al sistema principal: Si la aplicación utiliza campos de base de datos deAS/400 o importa archivos de pantalla de AS/400 cuando se está construyendo laaplicación, debe definir el sistema AS/400 que utiliza. Puede comunicar con elsistema principal en cualquier momento, siempre y cuando la información deconexión a servidores esté definida de la manera adecuada. Consulte el manualIniciación a VisualAge RPG y CODE/400 para obtener más información acerca de ladefinición de información de servidor.

Importación de archivos de pantalla de AS/400Si tiene un archivo de pantalla de AS/400 que contiene formatos de registro quedesea incluir en una ventana de diseño, puede importar dichos formatos deregistro desde un sistema AS/400 al entorno VisualAge RPG. Después decompletar la importación, el registro se convierte en un componente definido porusuario y se almacena en la página Importado del catálogo de componentes. Parapoder importar un archivo de pantalla de AS/400:v Defina el servidor (sistema AS/400) al que accederá. Consulte el apartado

Iniciación a VisualAge RPG y CODE/400, SC10-3287-01 (SC09-2625-01).v Debe tener un mínimo de autorización *USE para estos archivos de pantalla de

AS/400.

Para importar un archivo de pantalla:1. Elija Servidor→Importar archivo de pantalla en el Diseñador GUI.2. Seleccione un archivo de pantalla utilizando uno de los métodos siguientes:v Escriba el nombre completo del archivo de pantalla

(<servidor>biblioteca/archivo) en el campo de entrada Nombre del archivo ypulse Intro mientras el cursor esté en el campo.

v Haga lo siguiente:a. Seleccione uno de los servidores que se visualizan. Se visualiza una lista

de bibliotecas debajo del nombre del servidor.b. Seleccione uno de estos nombres de biblioteca. Aparecerá una lista de

objetos de archivo de pantalla.c. Seleccione uno de estos objetos de archivo de pantalla. Se visualiza una

lista de registros del archivo.3. Seleccione el registro que desea importar.

******************************************************************************************************************************************** Ventana . : PUR570R2 PO Header Maintenance ** *******************************************************************************************************************************************-*C PUR570R2 BEGACT CREATE PUR570R2c*c*C if #PONUM = 0C eval %setatr('pur570r2':'m2_change':'enabled')=0C eval %setatr('pur570r2':'m2_delete':'enabled')=0C eval %setatr('pur570r2':'m2_print':'enabled')=0C eval %setatr('pur570r2':'m2_fax':'enabled')=0C endC exsr POCHECKC write 'PUR570R2'C ENDACT*********************************************************************-

Figura 37. Ejemplo de subrutina de acción

206 Programación con VisualAge RPG

Page 225: c 0924494

4. Si no desea utilizar el nombre de componente por omisión, teclee un nombrede componente en el campo de entrada Nombre de componente.

5. Si no desea utilizar el icono por omisión, puede accionar el pulsador Find parautilizar la ventana Find an Icon.

6. Seleccione uno de los elementos siguientes para indicar dónde desea que residael componente:

Catálogo solamenteEl componente se añade a la página importada del catálogo.

Catálogo y paletaEl componente se añade a la página Importado del catálogo y el iconodel componente importado aparece en la paleta.

7. Elija Importar.

Conversión de archivos de pantallaAl importar un archivo de pantalla, se convierten los formatos de registro, camposy palabras clave que tienen atributos o componentes equivalentes y éstos puedenutilizarse como se utilizaría cualquier otro componente. Los formatos de registro,los campos y las palabras clave sin componentes equivalentes no se convierten.

En general,v Los formatos de registro se convierten en una ventana de VisualAge RPG o en

un grupo de componentes, dependiendo del tipo de registro.v Los campos se convierten en campos de entrada.v Las constantes se convierten en componentes texto estático.v Las opciones de indicador de condicionamiento no se tienen en cuenta.

Nota: Los campos cuya longitud sea superior a 64 bytes pasan a ser de 64 bytes enla GUI; no obstante, el atributo de longitud del cuaderno de propiedadesqueda establecido en la longitud original.

Formatos de registroLa siguiente lista describe cómo los formatos de registro de pantalla se conviertenen componentes.

MNUBAREl formato de registro MNUBAR se convierte en un componente de barrade menús que puede soltarse en una ventana con lienzo.

PULLDOWNEl formato de registro PULLDOWN se utiliza con el formato de registroMNUBAR para crear un componente submenú. El formato de registroPULLDOWN se convierte en componentes opción de menú para elformato de registro MNUBAR al que hace referencia.

RECORDEl formato de registro RECORD se convierte en un grupo de componentesque pueden soltarse en una ventana con lienzo.

SFL, SFLCTLEstos formatos de registro se convierten en un componente subarchivo quepuede soltar en una ventana con lienzo.

Las constantes de los registros SFL no se convierten.

WINDOWEl formato de registro de definición WINDOW se convierte en un

Capítulo 9. Reutilizar aplicaciones AS/400 207

Page 226: c 0924494

componente ventana con lienzo. El formato de registro de referenciaWINDOW se convierte en un grupo de componentes que pueden soltarseen una ventana con lienzo.

Los registros de formato que no se convierten son: ERRSFL, PDNSFL, SFLMSG,USRDFN y WDWSFL.

Entradas de posiciónLa siguiente tabla describe de qué manera las entradas de posición de DDSutilizadas para crear un archivo de pantalla determinan cómo se convierten losformatos y los campos.

Tabla 6. Entradas de posición y conversión

Columnas Significado Entrada y resultados de la conversión

8-16 IndicadoresNo se convierten

17 Tipo de registroR Se convierte según lo descrito

en Formatos de registro

H No se convierten

19-28 NombreSi es un campo con nombre, seutiliza como nombre delcomponente

29 ReferenciaR No se convierten

30-34 LongitudEstablece la longitud de losdatos

35 Modalidad de tecladoA Se convierte a carácter

E Tipo de datos establecidocomo DBCS cualquiera

G Tipo de datos establecidocomo Sólo DBCS

I Sólo lectura, inhabilitado

J Tipo de datos establecidocomo Sólo DBCS

O Tipo de datos establecidocomo DBCS mixto

D F M N S W X YNo se convierten

36-37 DecimalesDetermina el número deposiciones decimales delcomponente convertido. Si seespecifica, establece el tipo dedatos como Numérico.

208 Programación con VisualAge RPG

Page 227: c 0924494

Tabla 6. Entradas de posición y conversión (continuación)

Columnas Significado Entrada y resultados de la conversión

38 UsoI B Habilitado

M P No se convierten

O Sólo lectura, habilitado

H Se convierte si el campo es desubarchivo

39-41 UbicaciónDetermina la posición delcomponente en la ventana

45-80 Palabras claveConstante

Crea un componente textoestático

Palabras clave de archivos de pantallaLa siguiente lista describe cómo las palabras clave de archivo de pantalla seconvierten en componentes. Las opciones que se utilizan con estas palabras clavepueden determinar si las palabras clave se convierten o no.

CFnn, CAnnEstas palabras clave se convierten en pulsadores que tienen una etiquetaidéntica al nombre de la palabra clave.

CHOICEVea MLTCHCFLD y SNGCHCFLD.

CNTFLDLa palabra clave CNTFLD se convierte en un componente ediciónmultilínea.

COLORLa palabra clave COLOR determina el atributo de color de fondo delcomponente. Si hay más de una palabra clave COLOR, se utiliza la última.

COMPLa palabra clave COMP se utiliza para establecer los atributos decomparación en el cuaderno de propiedades del componente.

DATE La palabra clave DATE se convierte en un componente texto estático.

DFT El texto asociado con DFT se convierte en la etiqueta del componente.v Si el campo que está convirtiéndose es un campo de constante, en la

etiqueta se utiliza valor de DFT.v Si el campo que está convirtiéndose está especificado en un campo con

nombre, el valor de la palabra clave DFT se convierte en el texto poromisión del componente.

DFTVALEl valor de la palabra clave DFTVAL se convierte al valor por omisión delcomponente.

DSPATRSi el atributo de pantalla DSPATR es:v HI, el color de fondo se vuelve más brillante.

Capítulo 9. Reutilizar aplicaciones AS/400 209

Page 228: c 0924494

v ND, el campo convertido se establece como no visible.v PR, el campo convertido se establece como inhabilitado.

Los demás atributos de pantalla no se convierten.

HELP La palabra clave HELP se convierte en un pulsador con la etiqueta HELP.La función de ayuda no se convierte.

MLTCHCFLDSi se utiliza la palabra clave MLTCHCFLD en un registro PULLDOWN,cada una de las palabras clave CHOICE asociadas con ella se convierte enun componente opción de menú de un componente submenú. La parte deopción de menú convertida tendrá una marca de selección para indicar queestá activa.

Si la palabra clave MLTCHCFLD se utiliza fuera de un registroPULLDOWN, cada palabra clave CHOICE se convierte en un componenterecuadro de selección. Los recuadros de selección se colocan en sentidohorizontal, dejando entre ellos el mismo espacio. No se agrupan.

MNUBAREl formato de registro MNUBAR se convierte en un componente menú.

MNUBARCHCCada MNUBARCHC se convierte en un elemento de menú.

PRINTLa palabra clave PRINT se convierte en un pulsador con la etiqueta PRINT.La función de impresión no se convierte.

PSHBTNCHC, PSHBTNFLDLa palabra clave PSHBTNFLD se convierte en un componente pulsador. Eltexto asociado con la palabra clave PSHBTNCHC se convierte en laetiqueta de un componente pulsador.

PULLDOWNEl formato de registro PULLDOWN se utiliza con el formato de registroMNUBAR para crear un componente submenú. El formato de registroPULLDOWN se convierte en los componentes elemento de menú delformato de registro MNUBAR al que hace referencia.

RANGELa palabra clave RANGE se convierte en el atributo de rango delcomponente.

SFL, SFLCTLEstos formatos de registro se convierten en un componente subarchivo.

SFLPAGEjerce influencia en la altura inicial del componente subarchivo.

SNGCHCFLDSi se utiliza la palabra clave SNGCHCFLD dentro de un registroPULLDOWN, cada palabra clave CHOICE asociada con ella se convierteen un componente elemento de menú de un componente submenú.

Si la palabra clave SNGCHCFLD se utiliza fuera de un registroPULLDOWN, cada palabra clave CHOICE asociada con ella se convierteen un componente recuadro de selección. Los botones de selección sedisponen horizontalmente, dejando entre ellos el mismo espacio. No seagrupan.

210 Programación con VisualAge RPG

Page 229: c 0924494

SYSNAMELa palabra clave SYSNAME se convierte en un componente texto estático.

TIME La palabra clave TIME se convierte en un componente texto estático.

USER La palabra clave USER se convierte en un componente texto estático.

VALUESLa palabra clave VALUES hace que el campo se convierta en uncomponente recuadro de combinación desplegable. Los valores asociadoscon la palabra clave VALUES se utilizan en la lista desplegable.

WDWTITLELa palabra clave WDWTITLE se utiliza para determinar la etiqueta y losatributos de un componente ventana con lienzo.v Si el texto del título se asigna a un campo de programa a sistema, no se

convierte.v Si el texto del título se asigna a un campo literal, este texto se asigna a la

etiqueta del componente ventana con lienzo.

WINDOWEl formato de registro de definición WINDOW se convierte en uncomponente ventana con lienzo. El formato de registro de referenciaWINDOW se convierte en un grupo de componentes que pueden soltarseen una ventana con lienzo.

No se convierten más palabras clave.

Conversión del colorLos campos de entradas del monitor basado en caracteres se convierten encomponentes campos de entrada codificados por colores.

Nota: No todos los monitores dan soporte a dichos colores. En monitores VGA,por ejemplo, los campos de entrada convertidos serán de color blanco.

El color de cada campo de entrada convertido depende del tipo y de los atributosdefinidos en el archivo de pantalla:

Tabla 7. Atributos de campo originales y convertidos

Tipo de campo Atributos de campo Atributos GUI

E/S* ReadOnly: DesactivadoEnabled: ActivadoColor: Amarillo claro

Salida ReadOnly: ActivadoEnabled: ActivadoColor: Verde claro

Entrada ReadOnly: DesactivadoEnabled: ActivadoColor: Azul claro

Entrada o E/S Protegido ReadOnly: DesactivadoEnabled: DesactivadoColor: Rojo claro

Entrada o E/S Teclado inhibido ReadOnly: ActivadoEnabled: ActivadoColor: Rojo intermedio

Capítulo 9. Reutilizar aplicaciones AS/400 211

Page 230: c 0924494

Tabla 7. Atributos de campo originales y convertidos (continuación)

Entrada o E/S Teclado inhibido Protegido ReadOnly: ActivadoEnabled: DesactivadoColor: Rosa oscuro

Nota: E/S = entrada y salida

La codificación por colores le permite determinar visualmente los atributosestablecidos para el componente campo de entrada. Por ejemplo, si se visualiza uncampo de entrada verde claro, sabrá que lo utiliza el programa para visualizardatos y que no puede recibir ninguna entrada de usuario. Si se visualiza un camporojo claro, sabrá que puede recibir entradas de usuario pero que no está habilitadoporque se trata de un campo protegido de la aplicación original.

Reutilizar ayuda UIMPuede reutilizar la ayuda de AS/400 que se escribió utilizando el Gestor deInterfaz de Usuario (UIM) aunque los archivos de ayuda de VisualAge RPG seescriben utilizando el Recurso de Presentación de Información (IPF). Los formatosUIM y IPF utilizan principios de Lenguaje de Marcación General (GML) y sonaltamente intercambiables. Para obtener información detallada acerca de lautilización de IPF, consulte el manual Information Presentation Facility Guide andReference (disponible en línea). También debe consultar el documento en líneatitulado Restricciones de IPF. Este documento proporciona información detalladasobre el subconjunto de códigos IPF que le son restringidos en un entorno deWindows.

Para reutilizar archivos de ayuda de UIM en un sistema AS/400:1. Utilice el editor para copiar y pegar los miembros AS/400 que contengan la

ayuda UIM.2. Cambie los códigos UIM por los códigos IPF correspondientes.

En las secciones siguientes se comparan algunos de los códigos UIM e IPF.

Funciones UIM e IPF que utilizan los mismos códigosHay funciones en UIM e IPF que son equivalentes y se codifican exactamente de lamisma manera. En estos casos puede utilizar los códigos UIM literalmente.

Tabla 8. Códigos UIM e IPF idénticos

Código UIM Función código Código IPF

:DL. Lista de definiciones :dl.

:FIG. Figura :fig.

:HP1. Frase resaltada :hp1.

:HP2. Frase resaltada :hp2.

:HP3. Frase resaltada :hp3.

:HP4. Frase resaltada :hp4.

:HP5. Frase resaltada :hp5.

:HP6. Frase resaltada :hp6.

:HP7. Frase resaltada :hp7.

:HP8. Frase resaltada :hp8.

212 Programación con VisualAge RPG

Page 231: c 0924494

Tabla 8. Códigos UIM e IPF idénticos (continuación)

Código UIM Función código Código IPF

:HP9. Frase resaltada :hp9.

:LINES. Líneas :lines.

:LI. Elemento de lista :li.

:LP. Componente de lista :lp.

:NT. Nota :nt.

:OL. Lista ordenada :ol.

:P. Párrafo :p.

:PARML. Lista de parámetros :parml.

:P Descripción de parámetro :pd.

:PT. Término de parámetro :pt.

:SL. Lista sencilla :sl.

:UL. Lista no ordenada :ul.

:XMP. Ejemplo :xmp.

&AMP. Ampersand (&) &amp.

&COLON. Dos puntos (:) &colon.

&period. Punto (.) &period.

&SLR. Barra inclinada (/) &slr.

Funciones UIM e IPF equivalentes que utilizan códigosdistintos

Hay funciones en UIM e IPF que son equivalentes pero se codifican de maneradistinta. En esta situación, cambie la codificación UIM por la codificación IPFequivalente.

Tabla 9. Códigos UIM e IPF equivalentes

Código UIM Función Código IPF

:CIT. Cita :hp5.

:H1. Cabecera :h2.

:H2. Cabecera :h3.

:H3. Cabecera :h4.

:H4. Cabecera :h5.

:HELP. Cabecera :help.

:ISCH. Elemento índice :i1.

:ISCHSYN. Sinónimo de índice :isyn.

:PK. Palabra clave deprogramación

:hp2.

:PK. con :DEF. Palabra clave de prog. poromisión

:hp7.

:PV. Variable de programación :hp5.

Capítulo 9. Reutilizar aplicaciones AS/400 213

Page 232: c 0924494

Funciones UIM sin equivalentes IPFHay funciones disponibles en UIM que no están disponibles en IPF. En estasituación, suprima la función o busque otra manera de implantar la funciónutilizando la codificación IPF.

Tabla 10. Códigos UIM sin equivalentes IPF

Código UIM Función Sustitutos IPF sugeridos

:HP0. Sin resaltado No utilice ningún código :hpn alrededor deltexto.

:PC. Continuación de párrafo No utilice ningún código. Continúe con eltexto del párrafo.

:RT. Texto inverso Utilice un tipo diferente de resaltadoutilizando un código :hpn.

:XH1. Cabecera de ayuda general No hay ayuda general en IPF. Utilice uncódigo :link. para crear un enlace dehipertexto a otra ventana de ayuda (:h1.)donde se proporcione ayuda general.

:XH2. Cabecera de ayuda general No hay ayuda general en IPF. Utilice uncódigo :link. para crear un enlace dehipertexto a otra ventana de ayuda (:h1.)donde se proporcione ayuda general.

:XH3. Cabecera de ayuda general No hay ayuda general en IPF. Utilice uncódigo :link. para crear un enlace dehipertexto a otra ventana de ayuda (:h1.)donde se proporcione ayuda general.

:XH4. Cabecera de ayuda general No hay ayuda general en IPF. Utilice uncódigo :link. para crear un enlace dehipertexto a otra ventana de ayuda (:h1.)donde se proporcione ayuda general.

Reutilizar el fuente RPGPara reutilizar el código fuente RPG de un sistema AS/400:1. Si el código fuente no está en sintaxis RPG IV, conviértalo en sintaxis RPG IV

utilizando la herramienta de conversión de ILE RPG/400 (CVTRPGSRC) en elsistema AS/400.

2. Utilice el editor para copiar y pegar los miembros AS/400 que contengan elfuente RPG y subrutinas utilizadas habitualmente.

3. El comprobador de sintaxis resalta los códigos de operación que no esténsoportados por el compilador. Consulte el manual VisualAge RPG Manual deconsulta del lenguaje para obtener una descripción de los códigos de operaciónsoportados.

Nota: Además de las diferencias entre códigos de operación, existen otrasdiferencias entre el lenguaje RPG IV y el compilador VisualAge RPG quehay que tener en cuenta antes de reutilizar el fuente RPG. Para obteneruna descripción de las diferencias entre el lenguaje RPG IV y el lenguajeVisualAge RPG, consulte el manual VisualAge RPG Manual de consulta dellenguaje.

214 Programación con VisualAge RPG

Page 233: c 0924494

Parte 4. Temas avanzados“Capítulo 10. Depuración de la aplicación” en la página 217

Describe cómo depurar una aplicación.

“Capítulo 11. Edición de la salida” en la página 229Describe cómo formatear la salida.

“Capítulo 12. Utilización de archivos de imágenes, de sonido y de vídeo” en lapágina 233

Describe la utilización de archivos de imágenes y sonido en la aplicación.

“Capítulo 13. Consejos para crear ayuda en línea con IPF” en la página 235Describe cómo crear y utilizar ayuda en línea en la aplicación.

“Capítulo 14. Consejos para la creación y utilización de ayuda Windows” en lapágina 239

Describe cómo crear y utilizar ayuda de Windows en la aplicación.

“Capítulo 15. Consejos para la creación de JavaHelp” en la página 243Describe cómo crear y utilizar JavaHelp en la aplicación.

“Capítulo 16. Trabajar con mensajes” en la página 247Describe cómo crear y utilizar archivos de mensajes en la aplicación.

“Capítulo 17. Comunicación entre objetos” en la página 253Describe cómo establecer comunicación entre objetos de la aplicación.

“Capítulo 18. Cómo invocar métodos Java desde programas VisualAge RPG” enla página 269

Describe como invocar métodos Java.

“Capítulo 19. Consideraciones al compilar para Java” en la página 277Describe las restricciones de fuente RPG, cambios de fuente que puedanrequerirse y diferencias en el tiempo de ejecución para aplicaciones deJava.

“Capítulo 20. Llamada a funciones del sistema al compilar para Java” en lapágina 283

Describe cómo llamar a procedimientos externos mediante la InterfazNativa de Java (JNI).

“Capítulo 21. Cómo crear programas no GUI en VisualAge RPG” en lapágina 357

Describe cómo crear aplicaciones no GUI.

“Capítulo 22. Consideraciones sobre DBCS” en la página 363Describe cómo preparar la aplicación para su traducción.

“Capítulo 23. Fusión de código en la aplicación” en la página 367Describe cómo fusionar parte del código en la aplicación.

© Copyright IBM Corp. 1994, 2000 215

Page 234: c 0924494

216 Programación con VisualAge RPG

Page 235: c 0924494

Capítulo 10. Depuración de la aplicación

El depurador proporcionado con VisualAge RPG le ayuda a detectar y diagnosticarerrores en la aplicación. Puede utilizarse para depurar aplicaciones en las que sehan utilizado varios lenguajes. Puede:v Gestionar la ejecución de aplicaciones y DLL.v Establecer y controlar puntos de interrupción.v Visualizar y modificar estados del programa utilizando almacenamiento,

registros, variables y ventanas de pilas de llamadas.

En esta sección se muestran algunas de estas características cuando se utiliza unprograma VisualAge RPG.

Para depurar código Java generado por VARPG, necesitará Windows NT y elDistributed Debugger.

Arranque del depuradorPara arrancar el depurador, seleccione el elemento de menú Depurar del menúProyecto. Aparecen dos ventanas. La ventana Control de sesión de depuración yla ventana Fuente VisualAge RPG. La Figura 38 muestra estas dos ventanas.

Cuando se arranca el depurador, éste busca el miembro fuente VisualAge RPG ylo visualiza en la ventana Fuente. Una vez que el fuente se ha visualizado, puedeefectuar tareas de depuración.

Nota: Un número de línea resaltada indica la posición actual del programa enejecución. Aquí está resaltada la primera línea del miembro fuente.

Figura 38. Las ventanas Fuente VisualAge RPG y Control de sesión de depuración

© Copyright IBM Corp. 1994, 2000 217

Page 236: c 0924494

Visualización del código ensambladorSi el depurador no encuentra el fuente VisualAge RPG, carga el programa yvisualiza el código fuente ensamblador en lugar del código fuente VisualAge RPG.La ventana que se visualiza es parecida a la que se visualiza en la Figura 39.

Para corregir este problema, asegúrese de que el código fuente VisualAge RPG(archivo .VPG) reside en la estación de trabajo.

Carga de la aparición de DLLSi se visualiza el código fuente ensamblador significa que no se puede encontrar elmiembro fuente VisualAge RPG. Para solucionar este problema, seleccioneEstablecer aparición de carga en el menú desplegable Puntos de interrupción. Sevisualiza la ventana Punto de interrupción de aparición de carga (Figura 40 en lapágina 219). Desde esta ventana, puede cargar la aparición de DLL. Escriba lainformación siguiente y seleccione Bien:nombre_aplicación.DLL

Esto le devuelve a la sesión de depuración. Cuando la vista del fuenteensamblador se visualice de nuevo, pulse la tecla R para reanudar la ejecución delprograma. Cuando la DLL se carga, el sistema visualiza un mensaje y el nombre dela aplicación se visualiza en la ventana de control. Ahora puede pulsar el botón enla aplicación para que el fuente se visualice. Si el fuente no se visualiza significaque lo ha perdido o eliminado.

Figura 39. La ventana Desensamblar.

218 Programación con VisualAge RPG

Page 237: c 0924494

Si la aplicación utiliza el código de opción START para iniciar otro componente,tendrá que utilizar este procedimiento para cargar la DLL del otro componente.Esto le permitirá establecer puntos de interrupción dentro de otros componentes.

Entrada de información de arranque de la depuraciónSi no se puede localizar el archivo ejecutable, el depurador visualiza una ventanaparecida a la de la Figura 41 de más abajo. En esta ventana puede volver a entrarel nombre y los parámetros del programa.

Establecimiento de un punto de interrupciónEstableciendo puntos de interrupción puede controlar la manera en que suprograma se ejecuta. Un punto de interrupción detiene la ejecución del programaen una ubicación específica o cuando se produce un evento específico. Paraestablecer un punto de interrupción, mueva el cursor al número de línea en el quedesea efectuar la interrupción y efectúe una doble pulsación con el botón 1 delratón. El depurador resalta el número de línea mediante una marca roja. Puederepetir este proceso siempre que quiera marcar todas las líneas necesarias en lasque desea efectuar la interrupción. La Figura 42 en la página 220 muestra el aspectode la pantalla después de haber establecido varios puntos de interrupción. Puedevisualizar todos los puntos de interrupción en la ventana Lista de puntos deinterrupción.

Figura 40. Establecimiento del punto de interrupción de la carga de la aparición.

Figura 41. Información de arranque.

Capítulo 10. Depuración de la aplicación 219

Page 238: c 0924494

Seleccione Puntos de interrupción→Lista para visualizar esta ventana. Para cadapunto de interrupción se proporciona la siguiente información:v El estado de habilitaciónv El tipo de punto de interrupciónv La posición del punto de interrupciónv La condición debido a la que se activa el punto de interrupción

Figura 42. Establecimiento de varios puntos de interrupción.

Figura 43. La ventana Lista de puntos de interrupción.

220 Programación con VisualAge RPG

Page 239: c 0924494

Ejecución con puntos de interrupciónAl pulsar la tecla R se ejecuta el programa. Cuando encuentra el primer punto deinterrupción se para. Cuando el depurador encuentra un punto de interrupción, separa y resalta toda la línea, tal como se muestra en la Figura 44 de más abajo. Estoindica la posición en la que se ha detenido el programa en ejecución.

Utilización del ratón o del teclado para iniciar funciones de depuraciónLa mayoría de funciones de depuración pueden iniciarse utilizando el ratón o elteclado. Por ejemplo, para establecer una ubicación de punto de interrupción,efectúe una doble pulsación con el botón 1 del ratón en un número de línea.También puede establecer dicha ubicación seleccionando Línea en el menúdesplegable Puntos de interrupción. Cuando selecciona Línea, se visualiza laventana Puntos de interrupción de línea. A continuación debe entrar el número delínea. Cuando entra el número de línea y pulsa Intro, la línea que ha seleccionadose resalta en rojo.

Figura 44. Ejecución con puntos de interrupción.

Capítulo 10. Depuración de la aplicación 221

Page 240: c 0924494

También puede reanudar la ejecución del programa de maneras diferentes. Realiceuna de las acciones siguientes:v Pulse la letra R.v Mueva el ratón al menú desplegable Ejecutar y seleccione Ejecutar.v Mueva el ratón al icono de ejecución en la barra de herramientas y efectúe una

sola pulsación con el botón 1 del ratón.

Selección de opciones desde la barra de herramientasLa tabla siguiente lista todas las opciones disponibles en la barra de herramientas yexplica brevemente cada una.

Icono Función

Recorrer principalEjecuta la línea actual (resaltada) en el programa, pero no entra en ningunafunción llamada.

Recorrer todoEjecuta la línea actual (resaltada) en el programa y entra en cualquierprograma o función llamados.

Recorrer depuraciónEjecuta la línea actual (resaltada) en el programa. El depurador efectúa unaejecución de pasos externos en cualquier función para la que no hayinformación de depuración disponible, y efectúa una ejecución de pasosinternos en cualquier función para la que hay información de depuracióndisponible.

Figura 45. La ventana Puntos de interrupción de línea.

Figura 46. Opciones de la barra de herramientas.

222 Programación con VisualAge RPG

Page 241: c 0924494

Retorno de recorridoEjecuta de forma automática las líneas de código hasta la sentencia deretorno inclusive de la función actual.

EjecutarEmpieza la ejecución del programa en la línea actual (resaltada).

DetenerPara la ejecución del programa.

Vistas Conmuta a la vista siguiente.

Supervisar expresiónVisualiza una variable o una expresión en una ventana de supervisión.

Pila de llamadasVisualiza las funciones activas de la pila de llamadas de una línea deejecución.

RegistrosVisualiza los registros de las líneas de ejecución en la ventana de registros.

AlmacenamientoVisualiza el contenido del almacenamiento en la ventana dealmacenamiento.

Puntos de interrupciónLista todos los puntos de interrupción que se han establecido.

Control de sesión de depuraciónVisualiza la ventana de control de sesión de la depuración.

Visualización y modificación de variables, matrices y estructurasLa visualización de una variable, matriz u otra estructura VisualAge RPG válidadurante la depuración es una función utilizada habitualmente. La manera mássencilla de hacerlo consiste en mover el ratón a cualquier especificación en la quese permitan campos y efectuar una doble pulsación con el botón 1 del ratón. Porejemplo, mueva el ratón al indicador de condicionamiento, al factor 1, al factor 2,al campo de resultado y/o a los indicadores de resultado y efectúe una doblepulsación. Esto hace que se visualice el contenido de la especificación.

Nota: Si la variable es un operando para el código de operación EVAL, seleccionela variable que desea visualizar resaltándola con el ratón y a continuaciónefectúe una doble pulsación.

Si el campo o la estructura que desea visualizar o modificar está en la vista, lamanera más sencilla para visualizar su contenido es utilizar el ratón y efectuar unadoble pulsación en dicho campo o estructura. Sin embargo, si está utilizando unaprograma de gran tamaño y no puede localizar una variable o una estructuradeterminada con facilidad, seleccione Supervisar expresión del menú desplegableSupervisores (esto es lo mismo que pulsar Control-M).

En la ventana Supervisar expresión, que se muestra en la Figura 47 en lapágina 224, escriba la expresión, campo o estructura que desea visualizar y acontinuación pulse Intro.

Capítulo 10. Depuración de la aplicación 223

Page 242: c 0924494

Después de pulsar Intro, el campo o la estructura de VisualAge RPG se visualizaen la ventana Supervisor de programa, tal como se muestra en la Figura 48.

Modificación del contenido de un campo o de una estructuraUna vez que se ha visualizado un campo o una estructura de VisualAge RPG,puede modificar su contenido. Para hacerlo, efectúe una doble pulsación en elvalor en la ventana Supervisor de programa, escriba el valor nuevo y pulse la teclaIntro.

Modificación de la representaciónEl depurador le permite modificar la representación de cualquier variablevisualizada en el supervisor del programa. Los tipos de representación de unavariable o de una estructura pueden ser decimal, hexadecimal, binaria o de serie.Para modificar la representación, seleccione una variable en la ventana Supervisorde programa. A continuación, seleccione una representación en el menúEditar→Representación. El contenido de la variable se visualiza ahora en larepresentación que ha seleccionado.

Figura 47. La ventana Supervisar expresión.

Figura 48. La ventana Supervisor de programa.

224 Programación con VisualAge RPG

Page 243: c 0924494

Modificación de la representación por omisiónLas variables tienen tipos de representación por omisión. Por ejemplo, un campode tipo carácter se visualizaría en la ventana Supervisor de programa comocaracteres, no como hexadecimales. El depurador le permite alterar estecomportamiento. Tiene la opción de establecer la representación por omisión paracada tipo de datos. Para modificar la representación por omisión de un campo,seleccione Opciones→Valores de depurador→Representación de datos poromisión→Sistema. Se visualiza la ventana Representación de datos por omisión.

Visualización de punteros y almacenamientoEntre los tipos de datos que VisualAge RPG soporta están los punteros. LaFigura 49 muestra un ejemplo de visualización de un valor de puntero utilizandola ventana Almacenamiento. Seleccione Supervisor>Almacenamiento paravisualizar la ventana Almacenamiento.

Figura 49. Visualización de un valor de puntero.

Capítulo 10. Depuración de la aplicación 225

Page 244: c 0924494

Modificación de las vistas del depuradorEn la mayoría de ejemplos de esta sección se muestra la vista Fuente de VisualAgeRPG. El depurador también visualiza otras vistas: como la vista fragmentada y lavista combinada. Para modificar vistas, seleccione una opción del menú Ver, talcomo se muestra en Figura 50.

Figura 50. Modificación de vistas de depuración.

226 Programación con VisualAge RPG

Page 245: c 0924494

Establecimiento de fontsExisten muchas opciones disponibles en el depurador que le permiten personalizarla sesión de depuración. Por ejemplo, puede establecer los fonts que desee. LaFigura 51 visualiza la ventana de fonts. Para visualizar la ventana de fonts,seleccione Opciones→Valores de ventana→Fonts. En la ventana de fonts, seleccioneel font, el estilo y el tamaño que desee, y a continuación seleccione Bien. El fontmodifica la visualización en la sesión de depuración.

Figura 51. Establecimiento de fonts.

Capítulo 10. Depuración de la aplicación 227

Page 246: c 0924494

228 Programación con VisualAge RPG

Page 247: c 0924494

Capítulo 11. Edición de la salida

El compilador soporta posibilidades de edición que determinan cómo estánformateados los datos cuando se visualizan en los componentes campo de entraday texto estático. Para editar la salida, puede establecer códigos de edición opalabras de edición en el cuaderno de propiedades para estos componentes.

Los códigos de edición le permiten formatear datos de acuerdo con formatospredefinidos, mientras que las palabras de edición le permite definir el formatoque desee. Sólo puede especificar un código de edición o una palabra de ediciónpara un componente: no puede especificar ambos.

Los códigos y palabras de edición sólo se pueden especificar para los componentescampo de entrada y texto estático numéricos.

Cuando se leen datos de un campo de entrada formateado se lee en el programa,el compilador elimina todos los caracteres de edición antes de devolver los datos alprograma.

Nota: Las entradas de códigos de edición en la especificación de control de laaplicación se pasan por alto; no tienen ningún efecto en la salida de estoscódigos de edición.

Códigos de ediciónEstán soportados varios códigos de edición para formatear los datos en formatospredefinidos. Estos formatos insertan los separadores de millares y decimalesadecuados y determinan cómo se visualiza un número negativo, proporcionandoun signo menos fijo o flotante, o el símbolo CR (Crédito).

Opcionalmente, puede especificar protección por asteriscos o un símbolo demoneda flotante con los códigos de edición. Cuando se especifica la protección porasteriscos, se visualiza un asterisco por cada cero que se suprime. Cuando seespecifica el símbolo de moneda flotante, dicho símbolo aparece a la izquierda delprimer dígito significativo. El símbolo no visualiza un saldo cero cuando se utilizaun código de edición que suprime el saldo cero.

El sistema operativo determina los caracteres reales que se van a utilizar para losseparadores de millares y decimales y para el símbolo de moneda cuando seejecuta la aplicación.

© Copyright IBM Corp. 1994, 2000 229

Page 248: c 0924494

La siguiente tabla resume los códigos de edición soportados y la edición queproporcionan, y muestra algunos ejemplos.

Nota: El compilador no soporta códigos de edición definidos por usuario. Loscódigos de edición definidos por usuario se definen y se almacenan en elsistema AS/400 y no están disponibles para los programas VisualAge RPG.

Tabla 11. Códigos de edición VisualAge RPG

Cód.edic. Comas

Puntodecimal

Signo para saldonegativo

Ejemplo denúmero positivo

Ejemplo denúmero negativo

Saldocero

ning. No Sí Sí 0123456789 0123456789-

1 Sí Sí Sin signo 124,567.89 124,567.89 .00

2 Sí Sí Sin signo 124,567.89 124,567.89

3 No Sí Sin signo 124567.89 124567.89 .00

4 No Sí Sin signo 124567.89 124567.89

A Sí Sí CR 124,567.89 124.567,89CR .00

B Sí Sí CR 124,567.89 124.567,89CR

C No Sí CR 124567.89 124567,89CR .00

D No Sí CR 124567.89 124567,89CR

J Sí Sí -(menos) 124,567.89 124.567,89- .00

K Sí Sí -(menos) 124,567.89 124.567,89-

D No Sí -(menos) 124567.89 124567,89- .00

M No Sí -(menos) 124567.89 124567,89-

R Sí Sí -(menos flotante) 124,567.89 -124.567,89 .00

O Sí Sí -(menos flotante) 124,567.89 -124.567,89

E CT

No Sí -(menos flotante) 124567.89 -124567,89 .00

Q No Sí -(menos flotante) 124567.89 -124567,89

Y (2.) 1984-12-25

Z (3.) No No Sin signo 1234567 1234567

Notas:

1. Todos los códigos de edición suprimen los ceros iniciales2. El código de edición Y se utiliza para editar campos de fecha. El campo de

fecha debe definirse como campo numérico. La salida de este código de edicióntiene el formato nnnn-nn-nn. Este formato no puede modificarse. El sistemaoperativo determina el carácter de separador de fecha cuando se ejecuta laaplicación.

3. El código de edición Z elimina los signos + o −.

Palabras de ediciónPuede utilizar palabras de edición si ninguno de los códigos de ediciónsuministrados satisface sus requisitos de edición. Una palabra de edición es unmodelo que se aplica a los datos antes de colocarlos en el componente. Con laspalabras de edición, puede especificar:v Supresión de ceros inicialesv Asteriscos iniciales

230 Programación con VisualAge RPG

Page 249: c 0924494

v El símbolo de moneda fijo/flotantev La posición de los separadores de millares y decimales.

Nota: Cuando utilice palabras de edición, asegúrese de que especificacorrectamente los símbolos de moneda, decimales y de millares. Si lossímbolos no coinciden con la palabra de edición, obtendrá una salidaformateada incorrectamente, pero ningún error de tiempo de ejecución. Estossímbolos se sustituyen por los valores del sistema operativo de tiempo deejecución cuando se ejecuta la aplicación.

Partes de una palabra de ediciónUna palabra de edición se compone del cuerpo, el estado y la expansión. Estaspartes se muestran en el siguiente ejemplo:

x x x . x x $ 0 , x x & C R * x T O T A L| || || ||------------cuerpo-------------||-estado-||----expansión-----|

donde BLANCO = xSÍMBOLO DE MONEDA = $SEPARADOR MILLARES = .SÍMBOLO DECIMAL = ,

Cuerpo de una palabra de ediciónEl cuerpo es el espacio para los dígitos transferidos desde el campo de datos alcomponente. Comienza en la posición situada más a la izquierda de la palabra deedición. Contiene varios blancos más un cero o asterisco y el total equivale alnúmero de dígitos del campo de datos que ha de editarse.

Los caracteres siguientes tienen significados especiales cuando se utilizan en elcuerpo de una palabra de edición:

BlancoUn blanco se sustituye por el dígito de la posición correspondiente delcampo de datos.

Símbolo &El símbolo & causa un blanco en la pantalla editada.

Cero Un cero detiene la supresión de ceros. El cero es, por sí mismo, unaposición de dígito. Se visualizan los ceros que haya en el campo de datos ala derecha del carácter de detener supresión de ceros. Cada cero que sesuprime se sustituye por un blanco.

AsteriscoPuede utilizarse un asterisco en lugar de un cero como carácter de detenersupresión de ceros. Esto se denomina protección por asteriscos y cada ceroque se suprime se sustituye por un asterisco. Cualquier asterisco o cerosituado a la derecha del carácter de detener supresión de ceros es unaconstante y se visualizará tal cual.

Símbolo de modedaSi codifica un símbolo de moneda inmediatamente a la izquierda delcarácter de detener supresión de ceros, se insertará un símbolo de monedaen la posición situada a la izquierda del primer dígito significativo. Sedenomina símbolo de moneda flotante cuando se utiliza de esta manera. Sicodifica un símbolo de moneda en la posición situada más a la izquierdade la palabra de edición, es fijo y se visualiza siempre en la mismaubicación. Se denomina símbolo de moneda fijo.

Capítulo 11. Edición de la salida 231

Page 250: c 0924494

Separador de millares y separadores decimalesLos separadores de millares y decimales se visualizan en las mismasposiciones relativas en las que se codificaron en la palabra de edición.Todos los demás caracteres se visualizan si están a la derecha de los dígitossignificativos de la palabra de edición. Si están a la izquierda del dígitosignificativo de orden alto en la palabra de edición, se rellenan con blancoso se sustituyen por un asterisco si está utilizándose la protección porasteriscos.

Estado de una palabra de ediciónLas posiciones de estado visualizan el signo de los datos. El estado continúa a laderecha del cuerpo con un símbolo de crédito ( CR ) o menos ( - ). Estos dossímbolos sólo se visualizan cuando el campo es negativo. El símbolo ( & ) seutiliza para visualizar un blanco.

Expansión de una palabra de ediciónLas operaciones de edición no cambian las posiciones de expansión. La posición deexpansión comienza en la primera posición situada a la derecha del estado (ocuerpo, si el estado no está especificado). La expansión no puede contener blancos.Si se requiere un blanco, utilice un símbolo & en la palabra de edición.

232 Programación con VisualAge RPG

Page 251: c 0924494

Capítulo 12. Utilización de archivos de imágenes, de sonido yde vídeo

Los componentes control de animación, lienzo, pulsador gráfico, imagen, medios yelemento de menú le permiten visualizar imágenes en las ventanas al especificarun nombre de imagen válido en el atributo FileName.

Los formatos válidos de imágenes de Windows son:

Bitmaps de OS/2 y WindowsLas extensiones de archivo .BMP, .VGA, .BGA, .RLE, .DIB, .RL4 y .RL8 sereconocen como bitmaps de OS/2 o Windows.

Formato de iconoLa extensión de archivo .ICO se reconoce como un archivo de icono.

Formato de Intercambio de Gráficos de CompuServeLa extensión de archivo .GIF se reconoce como un archivo GIF.

Formato de Archivo de Imágenes de ZSoft PC PaintbrushLa extensión de archivo .PCX se reconoce como un archivo Paintbrush.

Formato de Archivo de Imágenes de Microsoft/AldusLas extensiones de archivo .TIF y .TIFF se reconocen como archivos TIFF.

Bitmap Targa/Vista de TruevisionLas extensiones de archivo .TGA, .VST y .AFI se reconocen como archivosTarga/Vista. Esta clase sólo soporta imágenes de 8 y 24 bits por plano.

Formato de Bitmap Intercalado IFF/ILBM de AmigaLas extensiones de archivo .IFF y .LBM se reconocen como archivos debitmap intercalado.

Bitmap X de WindowsLa extensión de archivo .XBM se reconoce como un archivo Bitmap X. Estaclase soporta bitmaps X10 y X11 de 1bpp. Algunos archivos .XBM quecontienen texto tienen el aspecto de sombras o iconos y no estánsoportados.

Segmento de Página de Impresora IBMLas extensiones de archivo .PSE, .PSEG, .PSEG38PP y .PSEG3820 sereconocen como archivos PSEG. Los archivos PSEG se utilizan para incluirdatos de imágenes en documentos BookMaster. Los archivos PSEG sólocontienen 1 bit por plano, que siempre es negro sobre blanco.

Los formatos válidos de imágenes Java son:v GIF (Formato de Intercambio de Gráficos) de CompuServev Formato Joint Photographic Experts Group (JPG, JPEG)

Además puede añadir sonido y vídeo mediante el componente medios, que dasoporte a los archivos WAV, .MID, .MPG, .MOV, .DAT y .AVI.

Al desarrollar una aplicación VisualAge RPG que incluya imágenes, sonido ovídeo, evite la codificación del atributo FileName para los componentes.Probablemente el usuario instalará la aplicación en un directorio diferente dedonde se desarrolló.

© Copyright IBM Corp. 1994, 2000 233

Page 252: c 0924494

Para asegurarse de que estos archivos estén localizables en tiempo de ejecución,utilice la serie Directorio actual (·\): un punto y una barra inclinada invertidaseguida del nombre de archivo. En tiempo de ejecución, el archivo se encuentra enel directorio actual desde el que se ejecuta la aplicación.

Por ejemplo, en el cuaderno de propiedades para un pulsador gráfico, especifiquelo siguiente como nombre de archivo para un icono denominado EXIT.ICO, de talmanera que se encuentre en tiempo de ejecución en el directorio actual.

.\\EXIT.ICO

Nota: Para las aplicaciones que se ejecutan en Windows, debe especificarse eldirectorio actual en el archivo AUTOEXEC.BAT.

Durante el tiempo de construcción, debe copiar los archivos de imágenes aldirectorio de tiempo de construcción para acceder a estos archivos.

Antes de empaquetar la aplicación para su distribución, copie todos los archivos deimágenes y sonido asociados en el subdirectorio de tiempo de ejecución adecuado(RT_JAVA o RT_WIN32) del proyecto, porque es este directorio el que seempaqueta y distribuye a otros usuarios. Vea “Parte 5. Distribución de laaplicación” en la página 397 para obtener instrucciones sobre el empaquetado de laaplicación.

Creación de iconos para WindowsSi tiene VisualAge para C++ para Windows, puede utilizar el programa de utilidadResource Workshop para crear iconos de Windows.

Conversión de iconos OS/2 a formato WindowsVisualAge RPG incluye un programa de utilidad para convertir iconos y bitmapsde OS/2 a versiones de Windows. Para obtener información específica sobre esteprograma de utilidad y sus parámetros, vaya al indicador del DOS y teclee IBMPCNV-H.

234 Programación con VisualAge RPG

Page 253: c 0924494

Capítulo 13. Consejos para crear ayuda en línea con IPF

Puede utilizar el Recurso de Presentación de Información (IPF) para crear ygestionar archivos de ayuda en línea para la aplicación. También puede utilizar IPFpara crear guías de aprendizaje y documentación en línea. Con VisualAge RPG, laayuda en línea creada será ayuda de Windows nativa.

En esta sección se introduce IPF y se dan algunos consejos para crear ayuda enlínea para la aplicación. Para obtener información detallada acerca de la utilizaciónde IPF, consulte el manual Information Presentation Facility Guide and Reference(disponible en línea). También debe consultar el documento en línea tituladoRestricciones de IPF. Este documento proporciona información detallada sobre elsubconjunto de códigos IPF que le son restringidos en un entorno de Windows.

También puede reutilizar el código fuente de ayuda UIM de un sistema AS/400.Consulte el apartado “Reutilizar ayuda UIM” en la página 212.

Creación de ayuda en líneaPara añadir ayuda en línea a un componente de la aplicación:1. Visualice el menú emergente del componente.2. Elija Texto de ayuda. Se abre una sesión de edición.3. Teclee el texto de ayuda según contexto para el componente.4. Codifique el texto de ayuda utilizando el lenguaje de codificación de IPF.5. Guarde la ayuda seleccionando Guardar en el menú Archivo.

Utilización de IPFEl fuente de los módulos de ayuda de aplicaciones VisualAge RPG está en formatoIPF. IPF le permite crear información en línea, especificar cómo aparecerá en lapantalla, conectar varias partes de la información y proporcionar información deayuda que el usuario puede solicitar. Las características del IPF incluyen:v Un lenguaje de codificación que formatea texto, proporciona maneras de

conectar unidades de información y personaliza ventanas.v Un compilador que crea documentos en línea y ventanas de ayuda.v Un programa que visualiza documentos en línea formateados.

Soporte de ayuda para otros idiomasPuede copiar y editar manualmente el archivo .VPF utilizando cualquier editor detextos. Sin embargo, no haga ninguna de las acciones siguientes:v Modifique o elimine el número que aparece después del texto res=. Ese número

es el identificador de recurso y el Diseñador GUI lo genera cuando usted crea laayuda para un componente. El identificador de recurso se utiliza para localizarel texto de ayuda adecuado. Si suprime o cambia un identificador de recurso, nose localizará el texto de ayuda perteneciente al mismo.

v Elimine la información de cabecera. Puede sustituir la información de cabeceracon el texto traducido.

© Copyright IBM Corp. 1994, 2000 235

Page 254: c 0924494

Adición de gráficos a la ayuda en líneaUtilice :artwork. para intercalar gráficos en los archivos fuente, como seanecesario. Los gráficos deben estar en formato bitmap (archivos .BMP).

Decisión del tipo de ayuda que se va a proporcionarLos usuarios pueden acceder a la ayuda de tres maneras diferentes en la aplicaciónVisualAge RPG:

Ayuda según contextoInformación de ayuda que se adapta al contexto actual de una opción ocomponente. El usuario puede acceder a este tipo de ayuda pulsando F1cuando una opción o un componente tiene foco. Puede proporcionar estaayuda a través del menú emergente del componente.

Ayuda a nivel de ventanaInformación acerca del propósito de una ventana. El usuario puede accedera este tipo de ayuda accionando un pulsador de ayuda. Puedeproporcionar esta ayuda creando el pulsador Ayuda y añadiendo lainformación de ayuda asociada.

Ayuda para tareasInformación acerca de tareas que el usuario puede realizar con laaplicación. El usuario puede acceder a este tipo de ayuda enlazando conotra información de ayuda desde un panel de ayuda. Puede suministraresta información creando información en línea y creando un enlace dehipertexto con ella desde el nivel de ventana o la ayuda según el contexto.Un enlace de hipertexto permite a un usuario saltar de un panel de ayudaa otro, o del texto seleccionado de un panel de ayuda a la informaciónrelacionada.

Ayuda para herramientasInformación al estilo de globos de ayuda acerca de las herramientas quepueden utilizarse. Para crear esta ayuda, vaya a la página ’general’ delcuaderno de propiedades de un componente y escriba una descripción dela herramienta (máximo de 15 caracteres) en el campo de entrada. Tambiénse puede utilizar un identificador de mensaje, como por ejemplo,*MSG0001, para especificar el texto de ayuda.

Adición de ayuda según el contextoPara añadir ayuda según el contexto para un componente, seleccione Texto deayuda del menú emergente del componente. Esto inicia una sesión de edición quecontiene información similar a la que se muestra en la Figura 52.

:h1 res=01· es un identificador de recurso que se genera automáticamente. Noedite este texto. Escriba una cabecera después de este código que identifique elpropósito del panel de ayuda y escriba el texto de ayuda después del código :p..

Creación de un pulsador de ayudaPara crear el pulsador Ayuda, seleccione un pulsador desde la paleta decomponentes con el botón derecho del ratón, mueva el puntero del ratón sobre la

:h1 res=01.PSB0000C:p.Ayuda

Figura 52. Sesión de edición para añadir ayuda en línea

236 Programación con VisualAge RPG

Page 255: c 0924494

ventana de diseño y vuelva a pulsar el botón derecho del ratón. Seleccione Textode ayuda en el menú emergente del pulsador para editar la información de ayuda.Establezca el atributo Help Enable para ese pulsador y el atributo Label para lapalabra Ayuda.

Creación de enlaces de hipertextoPara enlazar fragmentos de información de ayuda relacionados de manera que losusuarios puedan encontrar la información adecuada de forma rápida y fácil, utiliceun código de enlace en el texto de ayuda. Puede crear enlaces para un panel deayuda utilizando un idrec o idref.

Para enlazar con el panel de ayuda definido con un id=::link reftype=hd refid=search.Ventana Buscar:elink.

Para enlazar con el panel de ayuda definido con un res=::link reftype=hd res=15433.Pulsador Buscar:elink.

Capítulo 13. Consejos para crear ayuda en línea con IPF 237

Page 256: c 0924494

238 Programación con VisualAge RPG

Page 257: c 0924494

Capítulo 14. Consejos para la creación y utilización de ayudaWindows

Una de las características de VisualAge RPG es la posibilidad de crear ayudasensible al cursor para las aplicaciones. Puede crear la ayuda pulsando el botónderecho del ratón en un componente de la ventana de diseño y eligiendo Texto deayuda. Esta acción inicia el editor. El texto de la ayuda se escribe utilizando ellenguaje de marcas Information Presentation Facility (IPF). Durante el proceso dela construcción, el código fuente de la ayuda se compila para crear el archivo HLP.El lenguaje de marcas IPF se convierte en un archivo de ayuda con un aspectoOS/2 notable. Esta sección explica cómo crear ayuda auténtica de Windows para laaplicación.

Elementos necesarios

Se necesitan dos herramientas para crear un archivo de ayuda Windows:v Un procesador de textos que pueda guardar archivos en formato Rich Text

Format (RTF)v El compilador de ayudas Windows

El compilador de ayudas utiliza como entrada un archivo fuente de ayudaguardado en RTF. Son muchos los procesadores de texto que pueden guardararchivos en formato RTF; por ejemplo, Lotus WordPro, Microsoft Word yWordPerfect. Tenga en cuenta que el editor WordPad de Windows puede guardararchivos en formato RTF. Sin embargo, el formato RTF particular que utiliza nosirve para crear archivos de ayuda. No conserva muchas de las opciones deformato que necesita el compilador de ayudas para crear un archivo de ayuda.

El Help Compiler Workshop es una herramienta disponible en Microsoft queconsiste en un IDE para gestionar los archivos de ayuda, así como el compiladorde ayudas. Puede bajarse del FTP del compilador de ayudas de Microsoft en elURL:

ftp://ftp.microsoft.com/softlib/mslfiles/hcwsetup.exe

En el mercado existen numerosas herramientas, tanto comerciales como shareware,que proporcionan entornos completos de montaje de ayudas. Además, existenvarios libros que describen cómo utilizar la herramienta Help Compiler Workshop.Muchos de estos libros incluyen un CD-ROM con el Help Compiler Workshopcomo, por ejemplo, Microsoft Windows 95 Help Authoring Kit ISBN1-55615-892-0.

Pasos para la creación de ayuda Windows

Los pasos básicos que deben seguirse para utilizar ayuda Windows en la aplicaciónson los siguientes:1. Establecer el ID de recurso para cada componente que tendrá ayuda.2. Escribir el texto de ayuda.3. Crear el archivo de proyecto de la ayuda.4. Compilar el archivo de ayuda.

© Copyright IBM Corp. 1994, 2000 239

Page 258: c 0924494

Establecimiento del ID de recursoCada componente como, por ejemplo, un campo de entrada, un pulsador o unaventana, tiene un identificador asignado al que habitualmente se le hace referenciacomo un ID de recurso. VisualAge RPG asigna los ID de recurso automáticamentey no pueden modificarse. Para ver el ID de recurso de un componente, pulse conel botón derecho del ratón en el componente, en la ventana de diseño. SeleccionePropiedades para ver su cuaderno de propiedades. El ID de recurso es el númeroque aparece en la parte superior de la página General. En el siguiente ejemplo, esel número 19 situado junto al ID de componente:

Durante el proceso de la construcción, VisualAge RPG genera una entrada de tablade ID de recurso para cada componente para el que haya creado ayuda utilizandola opción de menú Texto de ayuda del menú emergente del componente. El motorde ayuda de Windows utiliza esta tabla para determinar el ID de recurso delcomponente, a fin de poder visualizar la ayuda correcta. Para que el componentetenga ayuda Windows, debe crear el texto de ayuda de cada componente de estaforma. Actualmente, VisualAge RPG no crea automáticamente esta entrada detabla. Si sigue este proceso, no se visualizará ninguna ayuda y no se generaráningún mensaje de error.

Escritura del texto de ayudaAntes de escribir la ayuda, deberá conocer unos pocos términos que utiliza laayuda de Windows. Antes de crear un archivo de ayuda Windows (extensión HLP)son necesarios los siguientes archivos:

Archivo de temasEste archivo contiene el texto de ayuda. El proyecto de ayuda puedeconsistir en uno o más archivos de temas. Los archivos de temas contienenuno o más temas. El archivo de temas se crea con el procesador de textos yse guarda en formato RTF (extensión RTF).

Archivo de proyectoEl archivo de proyecto contiene información acerca del archivo de ayuda.Contiene entre otras cosas los archivos de temas que deben incluirse. Elarchivo de proyecto lo mantiene el IDE de Help Workshop. Habitualmente,no se modifica directamente.

Archivo de contenidoSi desea tener una pestaña de Contenido cuando se visualice el archivo deayuda, debe tener un archivo de contenido. El archivo de contenidotambién lo crea y lo mantiene el IDE de Help Workshop.

El siguiente ejemplo muestra los pasos básicos en la creación de un archivo detemas con un tema. Tiene el texto de ayuda para el componente campo de entrada.Se ha utilizado Lotus WordPro para crear el archivo de temas. Cuando se abra el

Figura 53. Visualizar el ID de recurso

240 Programación con VisualAge RPG

Page 259: c 0924494

documento nuevo en el procesador de textos, escriba un título en la parte superiorde la página como, por ejemplo, Ayuda para el campo de entrada. A continuación deltítulo, escriba el cuerpo del texto de ayuda.

Cada tema debe tener un ID de tema. Un ID de tema es una nota al pie con elsímbolo #.

A continuación se indican los pasos para la creación de la nota al pie necesaria enWordPro. Siga los pasos correspondientes a su procesador de textos para crearnotas al pie con el símbolo #:

1. Coloque el cursor justo delante de la cabecera del tema.2. Seleccione Crear-Nota al pie/Nota final...3. En el diálogo Pies de nota, pulse Aceptar.4. El cursor se colocará al final del documento en la sección de notas al pie.5. Escriba el ID de tema: HelpForEF.6. Coloque el cursor al principio del ID de tema.7. Pulse el botón derecho del ratón y seleccione Propiedades del texto en el

menú emergente.8. En el diálogo Propiedades, seleccione la pestaña Viñetas y números.9. Marque el recuadro de selección Editar en página.

10. Escriba un carácter # delante del ID de tema.11. Cierre el diálogo Propiedades del texto.

El documento debe tener un aspecto similar al siguiente. Los datos que aparecen acontinuación de la línea es la nota al pie:

#Ayuda para el campo de entrada

Esta es la ayuda para el componente campo de entrada.

Más texto ...

________________________________________

#HelpForEF

En un archivo de temas puede tener varios temas. Cada tema debe empezar enuna página nueva. Una vez haya escrito el texto de ayuda, guarde el archivo detemas en formato RTF.

Creación del archivo del proyecto de ayudaA continuación se indican los pasos básicos para crear un archivo de proyectomínimo. Inicie Microsoft Help Workshop y realice lo siguiente:

1. Cree un archivo de proyecto nuevo eligiendo File-New y seleccionando Newproject. Se creará un proyecto nuevo.

2. Pulse el botón Files.3. En el diálogo Topic files, pulse Add... y añada el archivo de temas que acaba

de crear. Pulse OK para cerrar el diálogo Topic files.4. Pulse el botón Windows.5. En el diálogo Windows Properties, pulse Add para visualizar el diálogo Add a

New Window Type.6. Cree una ventana denominada main y cierre todos los diálogos hasta regresar

a Help Workshop.7. Correlacione el ID de tema (HelpForEF) del archivo de temas con el ID de

recurso del componente campo de entrada (12).8. Pulse el botón Map.9. En el diálogo Map, pulse Add.

Capítulo 14. Consejos para la creación y utilización de ayuda Windows 241

Page 260: c 0924494

10. Cuando aparezca el diálogo Add Map Entry, escriba HelpForEF en el campoTopic ID y 12 en el campo de valor numérico Mapped. Pulse OK.

11. Pulse OK para cerrar el diálogo Map.12. Guarde y compile el archivo de proyecto. De este modo se creará el archivo

de ayuda (HLP).

Copie el nuevo archivo HLP en el directorio RT_WIN32 del proyecto VARPG.

Compilación del programa VARPGDurante el proceso de la construcción, VisualAge RPG crea un archivo HLP en eldirectorio RT_WIN32. Este archivo, evidentemente, se grabará encima del archivoHLP que copió. Además, se creará un archivo RTF en el directorio fuente delproyecto. Si ha guardado el archivo de temas con el mismo nombre, se grabaráencima. Para evitarlo, abra el cuaderno de propiedades Opciones de laconstrucción del proyecto y diríjase a la página Archivo de ayuda. Desmarque elrecuadro de selección Crear archivo de ayuda RTF. Ahora, VisualAge RPG noconstruirá la ayuda ni creará los archivos RTF y HLP.

Cada vez que añada ayuda a un componente, debe volver a compilar el programaVARPG.

Prueba de la ayuda

Inicie la aplicación VARPG. Cuando aparezca la ventana, vaya al campo de entraday pulse F1. La ayuda debe visualizarse en una ventana de ayuda Windows.

También puede visualizar la ayuda como ayuda ¿Qué es esto?. Para ello, abra elcuaderno de propiedades de la ventana. En la página Estilo, marque el recuadrode selección Contexto. Deben quitarse las marcas de los recuadros de selecciónMinimizar y Maximizar.

Para hacer que la ayuda se visualice en una ventana emergente en lugar de unaventana de ayuda, marque la opción Emergente.

Creación de un archivo de contenidoSi desea que la ayuda tenga un recuadro de diálogo Temas de ayuda, deberá crearun Archivo de contenido. Un Archivo de contenido se crea en el IDE de HelpWorkshop cuando se selecciona Archivo-Nuevo y Archivo de contenido nuevo.Dé un nombre al archivo de contenido de la misma forma que ha hecho con elarchivo de ayuda y guárdelo en el mismo directorio.

242 Programación con VisualAge RPG

Page 261: c 0924494

Capítulo 15. Consejos para la creación de JavaHelp

Una de las características de VisualAge RPG es la posibilidad de dar servicio aJavaHelp sensible al contexto para las aplicaciones Java de VARPG. (VisualAgeRPG actualmente da soporte al release JavaHelp 1.1). Para construir y ejecutaraplicaciones Java de VARPG que incluyan JavaHelp, es necesario:v Un conocimiento básico de los códigos de HTML 3.2.v Archivos de metadatos de JavaHelp para la aplicación:

– Datos para la navegación - archivos de tablas de contenido (TOC)– Datos HelpSet data - archivos HelpSet y Map– Archivos de temas HTML

v Una copia del Java 2 Software Development Kit, Standard Edition (J2SDK)versión 1.2, o superior, instalada en la estación de trabajo. (El J2SDK estádisponible en Sun, en el URL http://www.javasoft.com/products/)

En esta sección se resume la creación de JavaHelp básica sensible al contexto paralas aplicaciones Java de VARPG. Si desea obtener información completa sobre elSistema JavaHelp, puede consultar la JavaHelp System User’s Guide. Toda ladocumentación de JavaHelp está disponible en el Sistema JavaHelp, que puedebajar del URL http://java.sun.com/products/javahelp.

Los siguientes pasos resumen la creación e incorporación de JavaHelp a laaplicación:1. Crear un HelpSet:v Crear los temas HTML.v Crear un archivo HelpSet.v Crear un archivo Map.v Crear un archivo de tabla de contenido (TOC).

Opcionalmente, puede crear un archivo de índice y una base de datos debúsqueda de texto completo. Consulte la JavaHelp System User’s Guide paraobtener detalles sobre estos temas y las herramientas necesarias paraimplementar la búsqueda.

v Comprimir y encapsular los archivos de ayuda en un archivo JAR.2. Tras crear la JavaHelp con todos los archivos necesarios y empaquetarlos en un

archivo JAR, copie este archivo JAR en el subdirectorio RT_JAVA del proyecto.3. Construir y ejecutar el proyecto.

El sistema JavaHelp se basa en archivos - los temas están dentro de archivos que sevisualizan en un visor adecuado, un archivo a la vez. Es una buena idea agrupartemas relacionados entre sí para tenerlos organizados y facilitar el enlace conjuntode los temas. También es importante organizar los temas de modo que puedanempaquetarse fácilmente en un JAR comprimido para la aplicación. Habitualmentelo mejor es organizar los temas en una jerarquía de carpetas que pueda ″despegar″y colocar en el archivo JAR.

La aplicación Video Store Catalog contiene archivos JavaHelp de ejemplo. Estánubicados en los subdirectorios javahelp y help del directorio adtswin\samples\vidcust.Puede utilizar estos archivos como plantillas para desarrollar sus ayudas JavaHelppersonales.

Nota: En Java, los nombres de archivo y carpeta son sensibles a las mayúsculas yminúsculas. Escriba los nombres exactamente como se muestran en losejemplos proporcionados.

© Copyright IBM Corp. 1994, 2000 243

Page 262: c 0924494

Creación de un archivo HelpSetCuando la aplicación inicia JavaHelp, lo primero que hace es leer el archivoHelpSet. El archivo HelpSet define el HelpSet para la aplicación: el conjunto dedatos que forman el sistema de ayuda. El archivo HelpSet incluye la siguienteinformación:

Archivo MapEl archivo Map, o de correlación, asocia los ID de tema al URL o nombrede vía de acceso de los archivos que contienen los temas HTML.

Información de visualizaciónDescribe los navegadores que se utilizan en el HelpSet. Los navegadoresestándares son: tabla de contenido, índice y búsqueda de texto completo.

Título del HelpSetEl nombre de la carpeta TOC de nivel superior.

ID inicialEl nombre del ID (por omisión) que se visualizará cuando se llame al visorde la ayuda sin especificar un ID.

El archivo HelpSet (nombrearchivo.hs) se codifica en formato Extended MarkupLanguage (XML). A continuación se ofrece un ejemplo de archivo HelpSet:<?xml version='1.0' encoding='ISO-8859-1' ?><!DOCTYPE helpsetPUBLIC "-//Sun Microsystems Inc.//DTD JavaHelp HelpSet Version 1.0//EN"

"http://java.sun.com/products/javahelp/helpset_1_0.dtd">

<helpset version="1.0">

<!-- title --><title>Video Store Catalog - Help</title>

<!-- maps --><maps>

<homeID>11</homeID><mapref location="Map.jhm"/>

</maps>

<!-- views --><view><name>TOC</name><label>Table Of Contents</label><type>javax.help.TOCView</type><data>VIDCTOC.xml</data>

</view>

</helpset>

Donde:

<title> Es el nombre del HelpSet. Corresponde al título de la ventana de ayuda.

<homeID>Especifica el nombre del ID (por omisión) que se visualiza cuando se llamaa la ayuda sin especificar explícitamente un ID.

<data>Especifica la vía de acceso de los datos que utiliza el navegador. Ennuestro ejemplo, la vista TOC. El nombre del archivo TOC está enmayúsculas y la extensión xml en minúsculas. El archivo TOC debe existiren el directorio de la ayuda.

244 Programación con VisualAge RPG

Page 263: c 0924494

Creación de un archivo MapCuando la aplicación activa JavaHelp, lo primero que hace es leer el archivoHelpSet de la aplicación. El siguiente paso consiste en leer el archivo Map que seindica en el archivo HelpSet. El archivo Map asocia los ID de tema con los URL(vías de acceso a los archivos que contienen los temas HTML). Por convenio, losnombres de archivo Map incluyen el sufijo jhm. El archivo Map está en formatoXML.

A continuación se ofrece un ejemplo de archivo Map:<?xml version='1.0' encoding='ISO-8859-1' ?><!DOCTYPE mapPUBLIC "-//Sun Microsystems Inc.//DTD JavaHelp Map Version 1.0//EN"

"http://java.sun.com/products/javahelp/map_1_0.dtd">

<map version="1.0"><mapID target="11" url="help/welcome.htm" /><mapID target="18" url="help/catalog.htm" /><mapID target="14" url="help/browse.htm" /><mapID target="15" url="help/new.htm" /><mapID target="16" url="help/top10.htm" /><mapID target="17" url="help/search.htm" />

</map>

target Especifica el ID del componente de VARPG. El ID de componente lo asignaautomáticamente el Diseñador GUI al componente. Puede recuperarlo delcuaderno de propiedades del componente.

url Especifica la vía de acceso al archivo de temas HTML que contiene el textode la ayuda. La vía puede ser relativa o absoluta.

Creación del archivo TOCEl archivo de tabla de contenido (TOC) describe el contenido y el diseño del TOCal navegador TOC. El archivo TOC está en formato XML. A continuación se ofreceun ejemplo pequeño de archivo TOC:<?xml version='1.0' encoding='ISO-8859-1' ?><!DOCTYPE tocPUBLIC "-//Sun Microsystems Inc.//DTD JavaHelp TOC Version 1.0//EN"

"http://java.sun.com/products/javahelp/toc_1_0.dtd"><toc version="1.0"><tocitem text="Video Store Catalog - help">

<tocitem text="Welcome" target="11"/><tocitem text="Help" target="22"/><tocitem text="Browse" target="14"/><tocitem text="New" target="19"/><tocitem text="Top 10" target="20"/><tocitem text="Search" target="21"/>

</tocitem></toc>

Donde:

tocitemLa primera entrada TOC especifica el título de la tabla de contenido.(Puede anidar entradas TOC dentro de una entrada de nivel superior).

text Especifica el texto que debe utilizarse en las siguientes entradas TOC.

Capítulo 15. Consejos para la creación de JavaHelp 245

Page 264: c 0924494

target Especifica el ID del tema HTML que debe visualizarse cuando el usuarioelija esta entrada en el TOC. El ID corresponde al ID de componente quese identifica en el archivo Map.

Creación del archivo JARUna vez haya creado todos los archivos de ayuda necesarios, utilice el mandato jarpara encapsular y comprimir los archivos. El nombre del archivo jar debe ser elsiguiente:SOURCE_FILE_NAMEHS

Donde SOURCE_FILE_NAME es el nombre especificado en el campo Archivo fuentede la ventana Guardar como aplicación - VisualAge para RPG. El nombre dearchivo debe acabar en HS y debe escribirse en mayúsculas. La extensión jar debeestar en minúsculas.

Emita el mandato desde el directorio más alto que contenga la jerarquía de laayuda. Por ejemplo, si la estructura del directorio de la ayuda es la siguiente:javahelp (directorio)

Map.jhmCATALOG.hsVIDCTOC.xml

help (subdirectorio)browse.htmcatalog.htmnew.htmsearch.htmtop10.htmwelcome.htm

Emita el mandato jar desde el directorio javahelp como se indica a continuación:jar -cf VIDCUSTHS.jar *.*

Copie el archivo jar resultante en el subdirectorio RT_JAVA del proyecto.Construya y ejecute el proyecto con la opción Java (Construir>Java oEjecutar>Java, respectivamente).

246 Programación con VisualAge RPG

Page 265: c 0924494

Capítulo 16. Trabajar con mensajes

Puede crear, ver, editar y suprimir mensajes para la aplicación VARPG.

Puede ver y suprimir mensajes existentes directamente desde la ventana Definirmensajes. Utilice la ventana Definir mensajes para acceder a la ventana Editarmensaje, desde donde puede crear un mensaje nuevo o modificar uno ya existente.

En VARPG los mensajes se dividen en dos grupos: aquellos a los que no se puedehacer referencia en el código en la ejecución y aquellos a los que sí.

El primer grupo consta de un mensaje de tipo etiqueta que se utiliza parareemplazar una etiqueta de sustitución en un pulsador o una ventana, por ejemplo.

El segundo grupo contiene cuatro tipo de mensajes: Acción, Grave, Información yAviso. Estos mensajes pueden visualizarse en una ventana de mensaje o en uncomponente subarchivo de mensajes. Pueden utilizarse para actualizar texto deforma dinámica en la interfaz en tiempo de ejecución; por ejemplo, para visualizarmensajes sobre el progreso de la instalación.

Definición de texto para etiquetas de sustituciónSi tiene que asociar texto con una etiqueta de sustitución:1. Asegúrese de que ha definido una etiqueta de sustitución en el componente.

Siga el procedimiento descrito en la publicación Iniciación a VisualAge RPG yCODE/400, SC10-3287-01 (SC09-2625-01).

2. Seleccione Proyecto→Definir mensajes en el Diseñador GUI. Se abrirá laventana Definir mensajes.

3. Seleccione un mensaje de tipo etiqueta en la lista que se visualiza.4. Elija el pulsador Editar. Se abre la ventana Editar mensaje, mostrando la

etiqueta que se ha seleccionado.5. En el campo Mensaje, teclee el texto de la etiqueta que se ha de sustituir.6. Seleccione Guardar para conservar los cambios o Cancelar ( o efectúe una

doble pulsación en el menú del sistema de la ventana) para desecharlos.

Nota: Al cambiar el tamaño de un componente en el Diseñador GUI que tengauna etiqueta de sustitución, tenga presente que el texto traducido puede sermás extenso que el original.

© Copyright IBM Corp. 1994, 2000 247

Page 266: c 0924494

Creación de un nuevo mensaje

Para crear un mensaje nuevo:1. Seleccione Proyecto→Definir mensajes en el Diseñador GUI. Se abrirá la

ventana Definir mensajes.2. Seleccione Crear. Se abrirá la ventana Editar mensaje.3. Seleccione un tipo de mensaje del recuadro desplegable Tipo. Puede elegir uno

de estos cuatro tipos:

Tipo de mensajeSignificado

AcciónUtilice este tipo de mensaje siempre el usuario deba realizar algunaacción para corregir la situación o elegir una acción alternativa.

Grave Utilice este tipo de mensaje siempre el usuario deba realizar una accióninmediata para corregir la situación o elegir una acción alternativa.

InformaciónUtilice este tipo de mensaje en situaciones en que simplemente deseeinformar al usuario de algo, pero en las que éste no ha de efectuarninguna acción.

Aviso Utilice este tipo de mensaje cuando el usuario pueda continuar con lasolicitud original sin efectuar ninguna modificación, aunque exista unasituación que el usuario debe tener en cuenta.

4. Teclee el texto del mensaje en el campo Mensaje.5. Si desea facilitar ayuda para el mensaje, teclee la ayuda en el campo Ayuda

para mensaje.Al crear una ayuda para mensaje y utilizar el código de operación DSPLY paravisualizar el mensaje, aparece el pulsador Ayuda en la parte inferior de laventana del mensaje. Cuando el usuario pulsa el botón en este pulsador, eltexto de ayuda se visualizará como información adicional.

6. Seleccione el recuadro de selección Movible si desea que el usuario puedamover el mensaje hasta el fondo y seguir con otras tareas antes de realizar unaacción con el mensaje.

7. En el recuadro desplegable Botones, seleccione la combinación de pulsadoresque desea que se visualice en la parte inferior de la ventana de mensaje:

OpciónPulsadores que aparecerán

abortRetryIgnoreButtonInterrumpir, Reintentar e Ignorar

okButtonAceptar

okCancelButtonAceptar y Cancelar

retryCancelButtonReintentar y Cancelar

yesNoButtonSí y No

yesNoCancelButtonSí, No y Cancelar

248 Programación con VisualAge RPG

Page 267: c 0924494

8. Seleccione un pulsador por omisión seleccionando el botón de selección Botón1, Botón 2 o Botón 3. Cuando se visualice la ventana de mensaje y el usuariopulse la tecla Intro, se realizará la acción asociada con el pulsador por omisión.Por ejemplo, si ha seleccionado enterCancelButton en el recuadro desplegablePulsadores y desea que el botón por omisión sea Cancelar, debería seleccionarel botón de selección Botón 2.

9. Seleccione Guardar para conservar el mensaje o Cancelar para desecharlo.

Nota: Los identificadores de mensaje (ID de mensaje) van de MSG0001 a MSG9999y los asigna VisualAge RPG. Si se utilizan todos los ID de mensaje delrango, VisualAge RPG envía un error cuando se intenta crear un nuevomensaje, y no se puede crear ningún mensaje nuevo hasta que suprime uno.Una vez que ha suprimido un mensaje, puede crear uno nuevo que utilice elID de mensaje del suprimido.

Edición de un mensaje

Para editar un mensaje:1. Seleccione Proyecto→Definir mensajes en el Diseñador GUI. Aparecerá la

ventana Definir mensajes.2. Seleccione un mensaje de la lista que se visualiza. Si no encuentra el que desea,

siga las instrucciones del apartado “Búsqueda de un mensaje”.3. Elija Editar en la ventana Editar mensajes. Se abre la ventana Editar mensaje,

mostrando el mensaje que se ha seleccionado.4. Cambie la información sobre el tipo, el texto, la ayuda o la ventana de mensaje.5. Seleccione Guardar para conservar los cambios o Cancelar para desecharlos.

Supresión de un mensaje

Para suprimir un mensaje:1. Seleccione Proyecto→Definir mensajes en el Diseñador GUI. Se abrirá la

ventana Definir mensajes.2. Seleccione un mensaje de la lista que se visualiza. Si no encuentra el que desea,

siga las instrucciones del apartado “Búsqueda de un mensaje”.3. Elija el pulsador Suprimir.

Búsqueda de un mensaje

A continuación se facilitan algunas sugerencias para localizar un mensaje:v Si sabe cuál es el ID de mensaje, utilice la característica Clasificar por ID de

mensaje de la ventana Definir mensajes. Los mensajes se clasifican por ID demensaje en orden ascendente.

v Si sabe el tipo de mensaje que está buscando, utilice la función Clasificar portipo de la ventana Definir mensajes. Los mensajes se clasifican por grupos y porID de mensaje en orden ascendente:1. Mensajes que se pueden establecer en la ejecución:

a. Informaciónb. Avisoc. Acciónd. Grave

2. Mensajes que no puede establecer durante la ejecución (etiquetas desustitución).

Capítulo 16. Trabajar con mensajes 249

Page 268: c 0924494

Puede desplazarse por la lista de mensajes utilizando las teclas de flecha o lasbarras de desplazamiento. Si la lista de mensajes es extensa, la barra dedesplazamiento es la forma más rápida de encontrar lo que se busca.

Utilización de mensajes con la lógica

Es habitual que en tiempo de ejecución se visualicen mensajes en ventanas demensajes. Una vez que se ha creado un mensaje, éste puede visualizarse medianteel código de operación DSPLY y el atributo de componente de subarchivo demensajes AddMsgID.

Si desea información sobre el atributo AddMsgID, consulte el apartado VisualAgeRPG Manual de consulta de componentes, SC10-3065-02 (SC09-2450-02) .

Puede utilizar las palabras clave MSGDATA y MSGNBR en la especificación de ladefinición para definir mensajes con variables de sustitución. Una variable desustitución se define cuando se crea el mensaje escribiendo el carácter deporcentaje ( % ) seguido de un valor numérico (por ejemplo, %1 %2 %3). Lavariable de sustitución se sustituye por el campo correspondiente definido en lapalabra clave MSGDATA. Por ejemplo, %1 se sustituiría por el primer campodefinido en MSGDATA, %2 por el segundo campo definido en MSGDATA, y asísucesivamente. La palabra clave MSGNBR debe contener un identificador demensaje de 8 caracteres; por ejemplo, *MSG0001.

Para utilizar la sustitución de mensajes en el código de operación DSPLY, defina untipo de datos de mensaje en la especificación D. Por ejemplo:DName+++++++++++ETDsFrom+++To/L+++IDc.Keywords+++++++++++++++++++++++++*

D notFound M MSGNBR(*MSG0001)D MSGDATA(cusno: file)*

Los campos CUSNO y FILE se definen en otro lugar del programa. Suponga que eltexto del mensaje *MSG0001 es:No se ha encontrado el número de cliente %1 en el archivo %2.

Para visualizar el mensaje con la operación DSPLY y llevar a cabo la sustitución,codifique lo siguiente en la especificación C:CSRN01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEqC notFound DSPLY rc 9 0

Para obtener más información sobre el código de operación DSPLY, consulte elmanual VisualAge RPG Manual de consulta del lenguaje, SC10-3066-01 (SC09-2451-01).

Conversión de archivos de mensajesNo es preciso que vuelva a compilar la aplicación para incorporar mensajestraducidos.

Se puede tener más de un archivo de mensajes en un directorio de tiempo deejecución; para ello, asigne una extensión diferente a cada archivo. Por ejemplo,una versión inglesa del archivo de mensajes compilado podría ser SAMPLE.ENG yuna versión alemana podría denominarse SAMPLE.GER. Puede indicar al usuariode la aplicación que redenomine el archivo de mensajes correspondiente aSAMPLE.MSG antes de ejecutar la aplicación.

250 Programación con VisualAge RPG

Page 269: c 0924494

Cambio manual de archivos de mensajesPuede editar manualmente el archivo ASCII ·TXM con el fin de traducirlo. Estearchivo contiene los mensajes que ha creado para la aplicación. Se crea en eldirectorio fuente que se especifica al crear la aplicación.

Un ejemplo del diseño de registros del archivo se muestra en la Figura 54.

Modifique únicamente el texto que figura detrás de los dos puntos ( : ).

El primer registro identifica el prefijo de mensaje y cada uno de los registrossiguientes identifica un mensaje de la aplicación.

Cada mensaje tiene un prefijo de mensaje, MSG, un identificador o número de IDde cuatro dígitos y una letra que describe el tipo de mensaje. En este ejemplo, elmensaje número 1 es un mensaje informativo y el mensaje número 2 es un mensajede aviso.

No haga lo siguiente:v Modificar el ID de mensaje. Si lo hiciese, los resultados serían imprevisibles. Sin

un ID de mensaje, no puede visualizarse el mensaje.v Añadir un mensaje. El estilo del mensaje no se definirá y éste nunca se

visualizará en la ventana Definir mensajes.v Suprimir un mensaje. La ventana Definir mensajes seguirá visualizándolo todo

acerca del mensaje, excepto su texto de mensaje.

Utilización de mensajes y etiquetasPuede establecer la etiqueta para cualquier componente que tenga un atributoLABEL del texto del mensaje en un archivo de mensajes. Cualquier etiqueta con elprefijo ‘*MSG’ indica el texto del mensaje de un archivo de mensajes. En el ejemplode la Figura 55, la etiqueta para el pulsador PB1 se ha establecido con el texto delnúmero de mensaje 0001 en el archivo de mensajes.

Si el número del mensaje no puede encontrarse en el archivo de mensajes delcomponente, la aplicación busca el archivo de mensajes indicado mediante elatributo MsgFile del *componente lógico para el número del mensaje. Si el númerodel mensaje no existe en el archivo de mensajes, el identificador del mensaje(MSG0001 en este ejemplo) aparece como el texto de la etiqueta.

MSGMSG0001I:Se ha guardado el archivo en el directorio de trabajo actual.MSG0002W:Otro usuario tiene abierto este archivo para editarlo.

Figura 54. Ejemplo de diseño de registros para un archivo TXM

C 'PB1' SETATR '*MSG0001' 'Label'

Figura 55. Establecimiento dinámico de una etiqueta de componente de un archivo demensajes

Capítulo 16. Trabajar con mensajes 251

Page 270: c 0924494

252 Programación con VisualAge RPG

Page 271: c 0924494

Capítulo 17. Comunicación entre objetos

Con VisualAge RPG puede realizar diversas clases de comunicaciones entre objetos

De componente a componentePuede enlazar componentes en VisualAge RPG de manera que uncomponente notifique a otro que ha cambiado, y que el componentedestinatario emita un evento cuando se le notifique de este cambio.

De aplicación VisualAge RPG a otras aplicaciones de PWSPuede hacer que una aplicación intercambie información con otraaplicación que soporte el protocolo DDE. Una aplicación VisualAge RPGpuede ser el cliente o el servidor en el intercambio. Para obtenerinformación sobre la función del cliente, vaya a “Cliente DDE” en lapágina 71. La función del servidor se describe en esta sección.

De componente lógico a componente lógicoPuede hacer que un componente lógico se comunique con otro.

También puede utilizar códigos de operación para realizar lo siguiente:v Llamar a funciones localesv Llamar a programas localesv Iniciar y detener componentes lógicosv Llamar a programas remotos

En esta sección se proporcionan sugerencias útiles para cada tipo de comunicacióny ejemplos.

Enlace de componentesLos siguientes componentes pueden enlazarse mediante VisualAge RPG:v Recuadro de selecciónv Campo de entradav Imagenv Recuadro de listav Mediosv Panel de mediosv Graduadorv Temporizador

Un componente que notifica a otro componente cuando se modifica se denominacomponente origen y el componente que recibe la notificación del cambio sedenomina componente destino.

Una manera de establecer comunicación entre un componente fuente y uncomponente destino es utilizar la página Enlace del cuaderno de propiedades delcomponente origen. En los campos que se proporcionan debe escribir el nombredel componente destino y el nombre de la ventana en el que reside. Si desea que eldestino emita un evento Link cuando recibe la notificación del componente fuente,seleccione el recuadro de selección Habilitar destino de notificación.

También puede configurar el enlace de comunicaciones en el programaestableciendo el atributo AddLink y el destino con el formatoNombreVentana|NombreComponente. Si desea que el destino emita un evento Link,

© Copyright IBM Corp. 1994, 2000 253

Page 272: c 0924494

establezca el atributo AllowLink en 1. La Figura 56 muestra el código de ejemploutilizado para enlazar un componente panel de medios, MMP1, con uncomponente medios, AUDIO1.

Nota: Sólo puede establecer un enlace para un componente origen en el DiseñadorGUI, pero puede establecer múltiples enlaces en el código.

Utilización de una aplicación VisualAge RPG como servidor DDECualquier aplicación VisualAge RPG puede ser un servidor en una conversaciónDDE (intercambio dinámico de datos).

Los componentes que pueden ser fuente de un evento LINK pueden producirdatos DDE. Un componente cliente DDE puede obtener datos de un componentelógico de la misma aplicación o una aplicación diferente. Para obtener másinformación acerca del componente cliente DDE, vea “Cliente DDE” en lapágina 71.

Por ejemplo, suponga que está construyendo una aplicación denominada CLIENT.Consiste en una ventana denominada WINDOW_C, un componente cliente DDEdenominada DDECLI_C, y un componente texto estático denominado STTEXT_C.

Suponga que la aplicación necesita datos de una aplicación servidora denominadaSERVER. Esta aplicación servidora tiene una ventana denominada WINDOW_S yun componente campo de entrada denominado ENTRY_S. Siempre que semodifique el valor del campo de entrada de la aplicación servidora, el componentetexto estático de la aplicación cliente se actualiza para reflejar el cambio.

Para establecer un enlace dinámico entre las aplicaciones cliente y servidor, deberíaespecificar los siguientes atributos del componente cliente DDE DDECLI_C en laaplicación cliente:

AppNameEs el nombre de la aplicación servidor: SERVER.EXE.

TopicEs el nombre del componente lógico servidor, seguido de una barra vertical,seguido del nombre de instancia de componente lógico. Para VisualAge RPG, en lamayoría de los casos el nombre de componente lógico es el mismo que el nombrede instancia de componente lógico y que el nombre ejecutable. En este ejemplo, elnombre del componente lógico es SERVER|SERVER.

ItemEs el nombre del componente servidor. Para los programas VisualAge RPG es elnombre de la ventana, seguido de una barra vertical, seguido del nombre decomponente. En este ejemplo, el valor del atributo del elemento esWINDOW_S|ENTRY_S.

*C 'MMP1' SETATR 'WIN2|AUDIO1' 'AddLink'C 'MMP1' SETATR 1 'AllowLink'*

Figura 56. Código de ejemplo que muestra un componente enlazado con otro

254 Programación con VisualAge RPG

Page 273: c 0924494

DDEAddLinkEs el nombre del componente cliente. Se compone del nombre de la ventana,seguido de una barra vertical, seguido del nombre de componente. En esteejemplo, el atributo DDEAddLink es WINDOW_C|STTEXT_C.

DDEModeEstablezca DDEMode en 1 para empezar la conversación e iniciar el enlacedinámico entre el servidor y el cliente. Para terminar la conversación, establezcaDDEMode en 2. Esto señala el evento Terminate en la aplicación cliente.

Comunicación entre componentes lógicosLos componentes lógicos son proyectos en VisualAge RPG. Representan una o másventanas de aplicación que se crearon con el Diseñador GUI. Un ejemplo decomponente lógico es una ventana que solicita a un usuario que entre el nombrede un archivo de imagen y luego visualiza la imagen. Para hacer que uncomponente lógico de VisualAge RPG se comunique con otro componente lógico,utilice un componente de referencia a componente lógico. Si desea másinformación, consulte la publicación “Referencia a componente lógico” en lapágina 62.

Realización de llamadas localesEn esta sección se analizan las llamadas locales que puede realizar utilizando estoscódigos de operación:

Código de operaciónPropósito

CALLBLlama a una función local. La función puede estar en un archivo de códigode objeto (OBJ) o exportarse desde una biblioteca de enlace dinámico(DLL).

CALLPLlama a un programa o función local (procedimiento). La función debeexportarse desde una biblioteca de enlace dinámico (DLL). Si desea másinformación, consulte la publicación “Utilización de múltiplesprocedimientos” en la página 264. Es preferible utilizar CALLP que utilizarCALLB.

STARTInicia un componente nuevo en la aplicación o llama a un programa local.

Utilización de la operación CALLBUtilice el código de aplicación CALLB para llamar a una función desde laaplicación VisualAge RPG. Si está enlazando con un OBJ que se compiló en unlenguaje distinto de RPG, asegúrese de que el entorno de tiempo de ejecución seinicializa y termina correctamente (vea la documentación del compilador paraobtener más información).

Los siguientes ejemplos ilustran las distintas maneras en que puede llamar a unafunción C utilizando CALLB. La Figura 57 en la página 256 contiene la función Cde ejemplo que se llama.

Capítulo 17. Comunicación entre objetos 255

Page 274: c 0924494

Llamada a funciones utilizando constantes con nombre oliteralesLos siguientes ejemplos ilustran cómo llamar a una función utilizando unaconstante con nombre o un literal:

#include <stdio.h>*

/*Las dos líneas siguientes sólo son necesarias si se compila *//*el OBJ con el compilador IBM C/C++. Estas líneas *//*no son necesarias si la función se exporta desde una DLL. */int _CRT_init(void);void _CRT_term(void);*

/* imprimir los parámetros str y age en un archivo */void MYFUNC(char *str, int *age) {

FILE *fp;int j;

*/*La línea siguiente sólo es necesaria si se compila *//*el OBJ con el compilador IBM C/C++. Esta línea *//*no es necesaria si la función se exporta desde una DLL. */

_CRT_init();*fp=fopen("myfunc.log", "a");

*/* imprimir los datos de caracteres en un archivo */for (j=0; j<10; ++j) {

fprintf(fp, "%c", str[j]);}

*/* si se da el parámetro age, imprimir el valor */if ( age == NULL ) {

fprintf(fp, "no hay valor para age\n");} else {

fprintf(fp, "num = %d\n", *age);}

*fclose(fp);

*/*La línea siguiente sólo es necesaria si se compila *//*el OBJ con el compilador IBM C/C++. Esta línea *//*no es necesaria si la función se exporta desde una DLL. */

_CRT_term();}

Figura 57. Función C de ejemplo, MYFUNC

256 Programación con VisualAge RPG

Page 275: c 0924494

Llamada a funciones utilizando un puntero de procedimientoEl siguiente ejemplo ilustra cómo llamar a una función utilizando un puntero deprocedimiento. Si se utiliza un puntero de procedimiento con CALLB, el campo*ROUTINE de la estructura de datos de estado de programa (PSDS) no se actualizacon el nombre de la función que está llamándose. El campo toma como valorespacios en blanco.

Llamada a funciones sin los parámetros obligatoriosEn el ejemplo siguiente se muestra cómo llamar a una función con un número deparámetros menor al obligatorio. Utilice el parámetro *OMIT que efectúa unacorrelación con un puntero NULL.

DConst1 C CONST('MYFUNC')Dwilma s 80a inz('misdatos')Dage s 9b 0 inz(32)**

C *inzsr begsrc***********************************************************************c*********** *** CALLB en VRPG con una PLIST *** *****************c***********************************************************************C myplist plistC parm wilmaC parm ageC CALLB Const1 myplistC seton lrC endsr

Figura 58. Llamada a funciones utilizando una constante con nombre

*Dwilma s 80a inz('misdatos')Dage s 9b 0 inz(32)C *inzsr begsrC callb 'MYFUNC'C parm wilmaC parm ageC seton lrC endsr

Figura 59. Llamada a funciones de biblioteca utilizando un literal

*Dp2 s * procptr inz(%paddr('MYFUNC'))Dwilma s 80a inz('misdatos')Dage s 9b 0 inz(32)C *inzsr begsrC callb p2C parm wilmaC parm ageC seton lrC endsr

Figura 60. Llamada a funciones utilizando un puntero de procedimiento

Capítulo 17. Comunicación entre objetos 257

Page 276: c 0924494

Llamada a programas locales utilizando CALLPUtilice CALLP para realizar llamadas a programas locales de manera síncrona. Estoquiere decir que el programa llamado completa la ejecución antes de que se ejecutela instrucción VisualAge RPG que sigue a CALLP.

Cada programa al que llame utilizando CALLP requiere un prototipo. El prototipodefine el nombre de sistema del programa llamado y el número y tipos deparámetros que el programa espera. Especifique este prototipo utilizando laespecificación de definición de tipo PR, que consiste en:

ColumnasDescripción

6 D

7-21 El nombre del programa a utilizar en el programa VisualAge RPG

24-25 PR

44-80 palabra clave

Utilice la palabra clave CLTPGM con el nombre de sistema del programa comoparámetro.

Si el programa espera parámetros, utilice una especificación de definición paracada parámetro inmediatamente después de la especificación de definición de PR.Estas especificaciones deben consistir en el nombre, la longitud y el tipo deparámetro. Especifique la precisión de los parámetros numéricos. Especifiquesiempre la palabra clave VALUE. También puede especificar las palabras claveASC, DATFMT, DESC, DIM, LIKE, NOOPT, OPTIONS y TIMFMT en lasdefiniciones de parámetros.

La Figura 62 define pgm1 para VisualAge RPG. Pueden pasarse dos parámetros alprograma; el segundo es optativo.

*Dp2 s * procptr inz(%paddr('MYFUNC'))Dwilma s 80a inz('misdatos')Dage s 9b 0 inz(32)C *inzsr begsrC callb p2C parm wilmaC parm *OMITC seton lrC endsr

Figura 61. Llamada a funciones sin los parámetros obligatorios

D pgm1 PR CLTPGM('testprog')D parm1 20A VALUED parm2 6B 3 OPTIONS(*NOPASS) VALUE

Figura 62. Especificación de parámetros de especificación de definición al llamar aprogramas locales

258 Programación con VisualAge RPG

Page 277: c 0924494

En la Figura 63, el código de operación CALLP llama a pgm1 con los parámetrosf1d1 y 22,4.

Para obtener más información sobre procedimientos, consulte “Utilización demúltiples procedimientos” en la página 264.

Llamada a programas locales utilizando STARTCuando utiliza el código de operación START para llamar a un programa,VisualAge RPG no espera a que el programa llamado acabe de ejecutarse, peroefectúa la llamada y continúa. A partir de ese punto, el programa llamado seejecuta independientemente del programa VisualAge RPG que ha efectuado lallamada.

Cuando se utiliza START, no es necesario establecer prototipos para programaslocales.

F2 puede ser un literal de tipo carácter, una constante con nombre o un nombre devariable.

Si F2 es un literal de tipo carácter, se supone que es un componente. Si es unnombre de constante y se especifica LINKAGE(*CLIENT) en la definición de laconstante, se supone que es un programa local. Vea la Figura 64.

Si F2 es un nombre de variable, se supone que es el nombre de componente amenos que se defina la variable en una especificación de definición conLINKAGE(*CLIENT) indicado. Puede utilizarse cualquier variable definida de estamanera como cualquier otro campo RPG. En la Figura 65, el primer código deoperación START intentará iniciar un componente y el segundo código deoperación START intentará iniciar un programa local.

C CALLP pgml(f1d1:22·4)

Figura 63. Llamada a programa local utilizando CALLP

D test1 C 'component'D test2 C 'testprog' LINKAGE(*CLIENT)*

*Para arrancar un componente:C START 'xxx'*

*Para arrancar un componente:C START test1*

*Arranca el programa local testprog.exe:C START test2

Figura 64. Ejemplo de utilización de START para llamar a programas locales

D name1 S 20AD name2 S 20A LINKAGE(*CLIENT)*

C START name1C START name2

Figura 65. Definición de nombres de variable para el código de operación START

Capítulo 17. Comunicación entre objetos 259

Page 278: c 0924494

START puede seguir teniendo una PLIST especificada en el campo de resultado opuede ir seguido de una lista de PARMS. Estos PARMS se pasan al componente oal programa local.

RESTRICCIONES PARA CALLP Y STARTTenga en cuenta estas restricciones al utilizar códigos de operación CALLP ySTART con programas locales:v La variable de entorno PATH se utiliza para encontrar el programa local si el

nombre de programa no se especifica con el nombre de vía de acceso completo.v El programa puede tener un máximo de 20 parámetros. En algunos casos, este

máximo es menos de 20 porque la serie de mandato no debe exceder de 1024bytes. (La serie de mandato se compone del nombre de programa y de losparámetros convertidos a caracteres.)

v Los punteros y los punteros de procedimiento no están permitidos comoparámetros. Todos los parámetros deben pasarse por valor.

v Cuando se utiliza START con un indicador de error para llamar a programaslocales, el indicador de error se establece en ON si no puede iniciarse elprograma local.

v LINKAGE(*SERVER) no es válido con el código de operación START.v Al especificar el nombre de un programa que va a llamar, incluya la extensión si

es distinta de EXE. Si no proporciona una extensión, se supone que es EXE. Porejemplo,

CLTPGM(’superc2’)Llama a SUPERC2.EXE

CLTPGM(’rexxpgm’)Llama a REXXPGM.EXE

CLTPGM(’rexxpgm.cmd’)Llama a REXXPGM.CMD

Esto se aplica al especificar el nombre de programa como una constante connombre para START, o al pasar el nombre de programa como una variable.

Inicio de componentes utilizando STARTUtilice el código de operación START para iniciar un componente nuevo en laaplicación y el código de operación STOP para terminar su ejecución. Para obteneruna descripción detallada de la sintaxis de estos dos códigos de operación,consulte el manual VisualAge RPG Manual de consulta del lenguaje.

La siguiente sección describe el funcionamiento de START y STOP con loscomponentes lógicos de la aplicación.

Inicio de un componenteEl código de operación START inicia un componente nuevo en la aplicación.Cuando se realiza la operación, tanto los componentes lógicos que se estániniciando como los ya iniciados, junto con cualquier otro componente lógico activode la aplicación, están listos para recibir acciones de usuario en todos loscomponentes actualmente habilitados por todos los componentes lógicos.

El código de operación START es similar al código de operación CALL en losiguiente:v Pueden pasarse parámetros a un componente lógico.v Los parámetros se correlacionan con los parámetros *ENTRY PLIST del

componente lógico destino.

260 Programación con VisualAge RPG

Page 279: c 0924494

v En el componente origen, el factor 2 del código de operación PARM se copia alcampo de resultado del mismo código de operación PARM. Cuando el control sedevuelve al componente lógico de origen, el campo de resultado se copia en elfactor 1.

v En el componente lógico de destino, el campo de resultado se copia en el factor1. Cuando el control se devuelve al componente lógico de origen, el factor 2 secopia en el campo de resultado si el componente lógico de destino completa uninicio satisfactorio.

v No se realizan comprobaciones ni conversiones en los parámetros.

El código de operación START es diferente del código de operación CALL en losiguiente:v Los términos llamado y de llamada se utilizan con el código de operación

CALL. Un programa llamado es un programa cuya ejecución se solicita desdeotro programa. Un programa de llamada es un programa que solicita laejecución de otro programa. Con el código de operación START, se utilizan lostérminos destino (llamado) y origen (de llamada).

v CALL invoca un programa, lo ejecuta y luego vuelve al programa de llamadacon el factor 1, factor 2 y el campo de resultado tal como se ha descritoanteriormente. START inicializa un componente lógico, ejecuta su *INZSR yvuelve al componente lógico origen con el factor 1, factor 2 y el campo deresultado copiado tal como se ha descrito anteriormente. La diferencia es quecon el código de operación START, el factor 2 del programa destino se copia alcampo de resultado al final de *INZSR (si *INZSR es satisfactorio), no al finaldel programa.

v Una vez que la operación START ha terminado de inicializar el componentelógico de destino, la subrutina de acción del componente lógico de origencontinúa ejecutándose y el componente lógico de destino permanece activo consus subrutinas de acción habilitadas para recibir eventos.

v Dado que los parámetros se pasan por dirección, los componentes lógicos deorigen y de destino pueden acceder a los parámetros pasados después de que laoperación START inicial ha finalizado. Esto quiere decir que los componenteslógicos de origen y de destino pueden continuar compartiendo informaciónutilizando los campos de parámetro.

Finalización de un componenteEl código de operación STOP termina la ejecución de un componente lógico. Si noespecifica el nombre del componente lógico en el factor 2, se termina elcomponente lógico que se ejecuta actualmente. Cuando se termina un componentelógico, los componentes hijos que puedan iniciarse son los primeros en terminar.

Cuando se realiza una operación STOP que afecta al componente lógico deejecución actual, no se ejecutan las operaciones que siguen a STOP. En otraspalabras, el resultado de STOP es inmediato. Por ejemplo, si COMPA iniciaCOMPB, y COMPB es el componente lógico que se está ejecutando actualmente yemite un STOP para COMPA, en primer lugar finaliza COMPB y después COMPA.No se realizan más operaciones a continuación de STOP.

La finalización de un componente lógico con STOP se considera una terminaciónnormal y se invoca *TERMSR para cualquier proceso de usuario final.

Llamada a programas remotosEsta sección analiza cómo la aplicación VisualAge RPG puede llamar a unprograma AS/400 y cómo una aplicación RPG que se ejecuta en un AS/400 puedellamar a una aplicación VisualAge RPG.

Capítulo 17. Comunicación entre objetos 261

Page 280: c 0924494

Llamada a programas AS/400Antes de que la aplicación pueda llamar a un programa AS/400, debe configurar elservidor.

El nombre del programa llamado puede ser el nombre de programa AS/400(opcionalmente calificado por biblioteca) o un nombre de alteración temporal.Puede definir la alteración temporal del programa mediante la página Programadel cuaderno Definir información de AS/400. Vea “Consideraciones sobre elcuaderno” en la página 189 para obtener información acerca de lo que sucede si lapágina de cuaderno no contiene un nombre de alteración temporal para el área dedatos.

La Tabla 12 y la Figura 66 en la página 263 muestran cómo llamar a un programaAS/400 utilizando un nombre de alteración temporal. El programa de la Figura 66en la página 263 llama a MYLIB/LOOKUP en SERVER01.

Tabla 12. Entre esta información en la página Programa

Nombre de alteración temporal delprograma:

REMPGM

Nombre del programa remoto: MYLIB/LOOKUP

Pseudónimo del servidor: SERVER01

262 Programación con VisualAge RPG

Page 281: c 0924494

Nota: Si el programa que está en el AS/400 contiene un archivo de estación detrabajo, causará una anomalía cuando el sistema intente abrirlo. Dado que elmandato de llamada remota se realiza a través del servidor DDM, eldispositivo de pantalla es desconocido para la gestión de datos de laestación de trabajo. Un procedimiento que puede utilizar consiste en crear elarchivo de estación de trabajo en el servidor AS/400 con el valor deDispositivo de pantalla establecido en el nombre de la sesión (OMXxxxx) yestablecer el parámetro Número máximo de dispositivo en un valor mayorque 1. Esto permitirá que puedan pasarse parámetros al programa AS/400.No intente obtener la sesión de manera explícita con una sentencia ACQ.Esto ocasionará un conflicto que producirá un error. Aún no puede adquirirningún dispositivo de pantalla de emulador 5250 en la estación de trabajo,porque causará un punto muerto que sólo puede finalizarse rearrancando laestación de trabajo.

Inicio de programas de estación de trabajo desde el AS/400Si tiene una aplicación RPG ejecutándose en el AS/400 y quiere iniciar unaaplicación VisualAge RPG en una estación de trabajo Windows, utilice el mandatoSTRPCCMD.

********************************************************************** ** ID de programa : rcallex.vpg ** ** Descripción . : Segmento de código para llamar a un programa ** remoto en el AS/400. ** ************************************************************************ REMPGM es el nombre de alias del programa remoto

D as400pgm S 6A INZ('REMPGM') LINKAGE(*SERVER)* Las variables siguientes son parámetros que se pasan al programa* remoto* student_id - input* name - output

D student_id S 6S 0 INZ(32533)D name S 20A********************************************************************** ** Ventana. . : WIN1 ** ** Componente : PSB0000C ** ** Evento . . : PRESS ** ** Descripción: Llame a un programa remoto en el AS/400 para obtener ** el nombre de la persona asociada al id. de estudiante** ***********************************************************************

C PSB0000C BEGACT PRESS WIN1C CALL as400pgmC PARM student_idC PARM nameC ENDACT

Figura 66. Llamada a un programa AS/400

Capítulo 17. Comunicación entre objetos 263

Page 282: c 0924494

Utilización de múltiples procedimientosLa posibilidad de codificar más de un procedimiento mejora considerablemente laposibilidad de codificar una aplicación modular.

Un programa de VisualAge RPG se compone de uno o más módulos. Unprocedimiento es una parte de código a la que puede llamarse mediante unallamada enlazada. VisualAge RPG tiene dos clases de procedimientos:procedimiento principal y subprocedimiento. Un procedimiento principal es unprocedimiento que puede especificarse como el procedimiento de entrada delprograma y recibe control cuando se le llama por primera vez. Tenga en cuentaque un procedimiento principal sólo se produce cuando se crea un EXE.

Un subprocedimiento es un procedimiento que se especifica después de la secciónfuente principal. Se diferencia de un procedimiento principal básicamente en que:v Los nombres que se han definido dentro de un subprocedimiento no son

accesibles desde fuera del mismo.v La interfaz de llamadas debe ser de prototipo.v Las llamadas a subprocedimientos deben ser llamadas de procedimiento

enlazadas.v Sólo pueden utilizarse las especificaciones P, D y C.

Los subprocedimientos pueden proporcionar independencia respecto a otrosprocedimientos porque los elementos de datos son locales. Los elementos de datoslocales se guardan por lo general en almacenamiento automático, lo que significaque un valor de una variable local no se conserva entre una llamada y otra alprocedimiento.

Los subprocedimientos proporcionan otra característica. Puede pasar parámetros aun subprocedimiento por valor y puede llamar a un subprocedimiento de unaexpresión para que devuelva un valor.

Llamadas de prototipoPara llamar a un subprocedimiento, debe utilizar una llamada de prototipo.También puede llamar a cualquier programa o procedimiento que se haya escritoen cualquier lenguaje mediante una llamada de prototipo. Una llamada deprototipo es aquella en la que la interfaz de llamadas se comprueba en el tiempode compilación utilizando un prototipo. Un prototipo es una definición de lainterfaz de llamadas. Incluye la información siguiente:v Si la llamada es enlazada (procedimiento) o dinámica (programa).v La manera de buscar el programa o el procedimiento (el nombre externo).v El número y la naturaleza de los parámetros.v Los parámetros que deben pasarse y los que se pasan de manera opcional.v El tipo de datos del valor de devolución, si hay alguno (para un procedimiento).

El compilador utiliza el prototipo para llamar al programa o al procedimientocorrectamente y para asegurarse de que el emisor pasa los parámetros correctos. LaFigura 67 en la página 265 muestra un prototipo para el procedimiento FmtCust,que formatea varios campos de un registro de manera legible. Tiene dosparámetros de salida.

264 Programación con VisualAge RPG

Page 283: c 0924494

Para producir los campos de salida formateados, FmtCust llama al procedimientoNumToChar. NumToChar tiene un parámetro de entrada numérico que se pasa porvalor y devuelve un campo de tipo carácter. La Figura 68 muestra el prototipo paraNumToChar.

Si el programa o el procedimiento son de prototipo, y desea utilizar el valor dedevolución, debe invocarlos con CALLP o en una expresión. Al pasar parámetrosde una lista, ésta debe seguir al nombre del prototipo, por ejemplo: nombre (parám1: parám2 : ...).

La Figura 69 muestra una llamada a FmtCust. Tenga en cuenta que los nombres delos parámetros, que se muestran en la Figura 67, no coinciden con los de lasentencia de llamada. Los nombres de los parámetros de un prototipo sólo seutilizan a efectos de documentación. El prototipo sirve para describir los atributosde la interfaz de llamadas. La definición real de los parámetros de llamada tienenlugar dentro del procedimiento mismo.

Utilizando llamadas de prototipo, puede llamar (con la misma sintaxis) a:v Programas que están en el sistema en el tiempo de ejecución.v Procedimientos exportados a otros módulos.v Subprocedimientos del mismo módulo.

Al objeto de formatear el nombre y la dirección adecuadamente, FmtCust llama aNumToChar para convertir el número de cliente en un campo de tipo carácter.Puesto que FmtCust utiliza el valor de devolución, la llamada a NumToChar tienelugar en una expresión. La Figura 70 en la página 266 muestra la llamada.

* Prototipo para el procedimiento FmtCust (Vea PR en la* especificación de la definición). Tiene dos parámetros.

D FmtCust PRD Nombre 100AD Dirección 100A

Figura 67. Prototipo para el procedimiento FmtCust

* Prototipo para el procedimiento NumToChar* El valor devuelto es un campo de tipo carácter de* 31 caracteres de longitud.

D NumToChar PR 31A* El parámetro de entrada se empaqueta con 30 dígitos y 0* posiciones decimales y se pasa por valor.

D NUMPARM 30P 0 VALUE

Figura 68. Prototipo para el procedimiento NumToChar

C CALLP FmtCust(RPTNAME : RPTADDR)

Figura 69. Llamada al procedimiento FmtCust

Capítulo 17. Comunicación entre objetos 265

Page 284: c 0924494

La utilización de procedimientos para valores de devolución, le permite escribircualquier función definida por el usuario que necesite. Además, utilizar unainterfaz de llamadas de prototipo abre una serie de opciones para pasarparámetros.v Los parámetros de prototipo pueden pasarse de varias maneras: por referencia,

por valor (sólo para procedimientos) o por referencia de sólo lectura. El métodopor omisión para RPG es pasar por referencia. Sin embargo, pasar por valor opor referencia de sólo lectura proporciona más opciones para pasar parámetros.

v Si el prototipo indica que está permitido para un parámetro determinado, puedeefectuar una o más de las acciones siguientes:– Pasar *OMIT.– Omitir un parámetro por completo.– Pasar un parámetro más corto del especificado (para parámetros de tipo

carácter y gráfico y para parámetros de matriz).

Consideraciones sobre el procedimientov No puede definir valores de devolución para un procedimiento principal. Los

parámetros deben pasarse por valor.v Un procedimiento principal sólo está contenido en un EXE. para el que se ha

especificado que su parámetro se pase por valor.v Cualquiera de las operaciones de cálculo pueden codificarse en un

subprocedimiento. Sin embargo, todos los archivos deben definirse globalmente,de manera que todas las especificaciones de entrada y salida deben definirse enla sección fuente principal. De la misma manera, todas las áreas de datos debendefinirse en el procedimiento principal aunque puedan utilizarse en unsubprocedimiento.

v La especificación de control sólo puede codificarse en la sección fuente principalya que controla todo el módulo.

v Se puede llamar a un subprocedimiento de manera recursiva. Cada llamadarecursiva hace que en la pila de llamadas se coloque una nueva invocación delprocedimiento. La nueva invocación tiene más almacenamiento para todos loselementos de datos del almacenamiento automático, el cual no está disponiblepara otras invocaciones porque es local. (Un elemento de datos que se hadefinido en un subprocedimiento utiliza almacenamiento automático a menosque la palabra clave STATIC esté especificada en la definición).El almacenamiento automático asociado con las primeras invocaciones no se veafectado por las más recientes. Todas las invocaciones comparten el mismoalmacenamiento estático, de manera que las invocaciones más recientes puedenafectar al valor retenido por una variable en un almacenamiento estático.

v Respecto al tratamiento de excepciones hay una diferencia entre elprocedimiento principal y el subprocedimiento, y es que éste no tienemanejadores de excepciones. Si se llamara al manejador por omisión para unprocedimiento principal se obtendría una terminación anormal delsubprocedimiento.

*--------------------------------------------------------------* CUSTNAME y CUSTNUM se han formateado para tener este aspecto:* A&P Electronics (Número de cliente 157)*--------------------------------------------------------------

C EVAL Name = CUSTNAME + ' 'C + '(Número de cliente 'C + %trimr(NumToChar(CUSTNUM)) + ')'

Figura 70. Llamada al procedimiento NumToChar

266 Programación con VisualAge RPG

Page 285: c 0924494

v Los nombres de los procedimientos de VisualAge RPG están en mayúsculas. Alllamar a estos procedimientos, debe asegurarse de especificar los nombres enmayúscula.

Implicaciones del procedimientoComo programador, tiene la opción de producir tres objetos destino posibles:v Una DLL de VisualAge RPG (contiene códigos de operación de GUI)v Una DLL de utilidad que contiene sólo subprocedimientos de RPG que no

incluyen ningún código de operación de GUI.v Un EXE de RPG que no contiene ningún código de operación de GUI.

Consideraciones sobre las DLL de VisualAge RPGv Los subprocedimientos DLL de VisualAge RPG no son externos.

El compilador ha especificado que estos subprocedimientos son sólo internos.Los puntos de entrada no son externos para otros módulos. Cualquier intento deenlazar estos subprocedimientos ocasionará un error en el paso de enlace.

v La palabra clave EXPORT no está permitida en especificaciones deprocedimiento puesto que los procedimientos no pueden exportarse desde unaDLL de VisualAge RPG.

Consideraciones sobre la DLL de utilidadEsta DLL se crea cuando se proporciona la palabra clave NOMAIN en laespecificación de control.

El compilador producirá una DLL y un archivo LIB como resultado de lacompilación. El archivo LIB contendrá todos los procedimientos que tienen lapalabra clave EXPORT en su especificación P inicial. El archivo LIB le permiteenlazar a los subprocedimientos contenidos en la DLL.v La DLL se compone sólo de procedimientos.

Todas las subrutinas (BEGSR) deben ser locales para un procedimiento.v No se permiten códigos de operación GUI en el fuente.

Esto incluye START, STOP, SETATR, GETATR, %SETATR, %GETATR,SHOWWIN, CLSWIN y READS. Puede utilizarse DSPLY, pero si se llama alprocedimiento que lo contiene desde una DLL de VisualAge RPG, el código deoperación DSPLY no realizará ninguna acción.

v *inzsr y *termsr no están permitidos.v *ENTRY parms no está permitido.v El tratamiento de excepciones se diferencia de la DLL de VisualAge RPG en lo

siguiente:– No se devuelve ninguna información sobre la excepción al emisor si éste no

reside en la DLL de utilidad.– La manera más adecuada para que un usuario trate excepciones en una DLL

de utilidad es tener un indicador de errores, o un *PSSR local para cadarutina que devuelva un código de devolución apropiado al emisor.

– El manejador de excepciones por omisión no se invoca nunca desde una DLLde utilidad ya que no se invoca cuando se produce una excepción en unprocedimiento. Si se produce una excepción en la DLL de utilidad y no hayningún indicador de errores ni *PSSR, tiene lugar un exit() y la informaciónsobre la excepción se graba en el archivo FVDCERRS.LOG.

Consideraciones sobre el EXEv El EXE se crea cuando se proporciona la palabra clave EXE en la especificación

de control.v El EXE se compone sólo de procedimientos.

Capítulo 17. Comunicación entre objetos 267

Page 286: c 0924494

Todas las subrutinas (BEGSR) deben ser locales para un procedimiento. El EXEdebe contener un procedimiento cuyo nombre coincida con el nombre delarchivo fuente. Éste será el punto de entrada principal para el EXE (por ejemplo,el procedimiento principal).

v No se permiten códigos de operación GUI en el fuente.Esto incluye START, STOP, SETATR, GETATR, %SETATR, %GETATR,SHOWWIN, CLSWIN y READS. Se puede utilizar DSPLY.

v *inzsr y *termsr no están permitidos.v *ENTRY parms no está permitido.

Si hay parámetros de entrada, están especificados en la definición de parámetrosdel procedimiento principal y deben pasarse por VALUE (la palabra claveVALUE debe especificarse para cada parámetro).

v La palabra clave EXPORT no está permitida en la especificación P Begin.v El tratamiento de excepciones se diferencia de la DLL de VRPG. El manejador de

excepciones por omisión no se invoca nunca desde un EXE. Si se produce unaexcepción en el EXE y no hay ningún indicador de errores ni *PSSR, tiene lugarun exit() y la información sobre la excepción se graba en el archivoFVDCERRS.LOG.

268 Programación con VisualAge RPG

Page 287: c 0924494

Capítulo 18. Cómo invocar métodos Java desde programasVisualAge RPG

Esta sección describe cómo invocar métodos Java desde programas VARPG que sehan convertido a código fuente Java, así como los elementos adicionales dellenguaje VARPG que dan soporte a estas funciones. Para invocar métodos Java, elcompilador VARPG necesita la siguiente información:v El nombre del métodov La clase que contiene el métodov La clase del objeto devuelto si el método devuelve un objetov Si el método es estático o nov Los tipos de datos de los parámetros pasado al método

Además, si el método no es estático, debe crearse una instancia para un objeto parapoder invocar el método. Si el método devuelve un objeto, el compilador debetener dónde almacenarlo. Si el método acepta un objeto como parámetro, debehaber alguna forma de crear ese objeto.

Estos requisitos han conducido a los siguientes elementos adicionales en ellenguaje VARPG:v El tipo de datos de objetov La palabra clave CLASSv La extensión de la palabra clave EXTPROC

El tipo de datos de objeto y la palabra clave CLASSLos campos que pueden almacenar objetos se declaran utilizando el tipo de datosO. Para declarar un campo de tipo O, codifique O en la columna 40 de laespecificación D y utilice la palabra clave CLASS para proporcionar la clase delobjeto. La palabra clave CLASS acepta dos parámetros:CLASS(*JAVA:nombre de clase)

*JAVA identifica el objeto como objeto Java. El nombre de clase especifica la clasedel objeto. Debe ser literal en los caracteres y el nombre de clase debe sertotalmente calificado. El nombre de clase es sensible a las mayúsculas yminúsculas.

Por ejemplo, para declarar un campo que contendrá un tipo de objeto BigDecimal:D bdnum S O CLASS(*JAVA:'java.math.BigDecimal')

Para declarar un campo que contendrá un tipo de objeto String:D string S O CLASS(*JAVA:'java.lang.String')

Observe que ambos nombres de clase están totalmente calificados y que el uso demayúsculas y minúsculas coincide exactamente con el de la clase Java.

Los campos de tipo O no pueden definirse como subcampos de estructuras dedatos. Es posible disponer de matrices de campos de tipo O, pero no estánpermitidas las tablas de tipo O porque deben cargarse en tiempo de ejecución.

Las palabras clave siguientes no pueden utilizarse con la palabra clave CLASS:

© Copyright IBM Corp. 1994, 2000 269

Page 288: c 0924494

ALIGN, ALT, ASCEND, BASED, BUTTON, CLTPGM, CONST, CTDATA, DATFMT,DESCEND, DTAARA, EXTFLD, EXTFMT, EXTNAME, FROMFILE, INZ, LINKAGE,MSGDATA, MSGNBR, MSGTEXT, MSGTITLE, NOOPT, NOWAIT, OCCURS, OPTIONS,OVERLAY, PACKEVEN, PERRCD, PREFIX, PROCPTR, STYLE, TIMFMT, TOFILE,VALUE, VARYING

Cómo realizar el prototipo de un método JavaAl igual que los subprocedimientos, los métodos Java deben ser prototipos paraque puedan ser invocados correctamente. El compilador VARPG debe conocer elnombre del método, la clase a la que pertenece, los tipos de datos de losparámetros y el tipo de datos del valor de retorno (si lo hubiera), así como si elmétodo es estático o no.

La palabra clave EXTPROC extendida puede utilizarse para especificar el nombredel método y la clase a la que pertenece. Al hacer un prototipo de un método Java,el formato de la palabra clave EXTPROC debe ser:EXTPROC(*JAVA:nombre_clase:nombre_método | *JAVARPG:nombre_clase:nombre_método)

*JAVARPG identifica el método como un método Java generado por VARPG.*JAVA identifica el método como un método Java que ha sido generado de códigoescrito inicialmente en Java y no generado por VARPG. Esta distinción esimportante porque los métodos generados a partir de *JAVARPG permitirán queciertos tipos de datos sean pasados por referencia cuando normalmente no podríanpasarse por referencia en Java. Ello permite que pueda utilizarse el mismo códigofuente al dirigirse a Windows y al generar código fuente Java.

Tanto el nombre de clase como el del método deben ser literales en el uso demayúsculas y minúsculas. El nombre de clase debe ser un nombre de clase Javatotalmente calificado y es sensible a las mayúsculas y minúsculas. El nombre demétodo debe ser el nombre del método que debe invocarse y es sensible a lasmayúsculas y minúsculas.

La forma extendida de la palabra clave EXTPROC sólo puede utilizarse al invocarmétodos Java. Si se dirige a Windows, el uso de esta forma de la palabra claveEXTPROC dará como resultado un error del compilador.

Los tipos de datos de los parámetros y el valor de retorno del método estánespecificados de la misma forma que la realización de un prototipo de unsubproceso. La única observación al respecto es que los tipos de datos secorrelacionan a tipos de datos Java. El compilador correlaciona tipos de datosVARPG a tipos de datos Java según se muestra a continuación:

Tipo de datos Java Tipo de datos VARPG

char[] gráfico o Unicode

boolean indicador (N)

byte[] alfanumérico (A de cualquier longitud)

byte entero (3I)

int entero (10I)

short entero (5I)

long entero (20I)

float coma flotante (4F)

double coma flotante (8F)

270 Programación con VisualAge RPG

Page 289: c 0924494

Tipo de datos Java Tipo de datos VARPG

cualquier objeto objeto (O)

Los tipos de datos con zona, empaquetados, binarios y sin signo no estándisponibles en Java. Si pasa un campo con zona, empaquetado, binario o sin signocomo parámetro, el compilador realizará la conversión apropiada, pero es muyposible que provoque truncamiento y/o pérdida de precisión.

Si el método que está invocando ha sido generado por VARPG, es decir, que hasido especificado como primer parámetro de una palabra clave EXTPROC,entonces los tipos de datos con zona, empaquetados, binarios y sin signo puedenespecificarse como tipo de datos de los parámetros y los valores de retorno. Losmétodos generados por código escrito inicialmente en Java no pueden utilizar tiposde datos con zona, empaquetados, binarios y sin signo en el prototipo paraparámetros o valores de retorno.

Al invocar un método, el compilador acepta matrices como parámetros si éste esun prototipo que utiliza la palabra clave DIM. En caso contrario, sólo se aceptaránlos campos escalares, las estructuras de datos y las tablas.

Actualmente, no puede invocar métodos que esperen estos tipos de datos de Java oque devuelvan estos tipos de valores: byte, char y long.

Si el valor de retorno de un método es un objeto, entonces usted debe proporcionarla clase del objeto codificando la palabra clave CLASS en el prototipo. El nombrede clase especificado será el del objeto que se devuelve. Utilice la palabra claveEXTPROC para especificar la clase del método que se invoca.

Si el método invocado es estático, entonces debe especificar la palabra claveSTATIC en el prototipo.

En Java, los tipos de datos siguientes sólo pueden pasarse por valor:byteintshortlongfloatdouble

Estos tipos de parámetros deben tener asignada una especificación de la palabraclave VALUE en el prototipo.

Si el método que está invocando ha sido generado por VARPG, es decir, que hasido especificado como primer parámetro de una palabra clave EXTPROC,entonces estos tipos de datos pueden pasarse por referencia y la palabra claveVALUE no es necesaria.

Observe que sólo se puede pasar los objetos por referencia. La palabra claveVALUE no puede especificarse con tipo O. Debido a que java percibe las matricescomo objetos, los parámetros que correlaciones a matrices deben también pasarsepor referencia. Esto incluye a las matrices de bytes.

Ejemplos de cómo realizar el prototipo de un método JavaEsta sección presenta algunos ejemplos de prototipo de métodos Java.

Capítulo 18. Cómo invocar métodos Java desde programas VisualAge RPG 271

Page 290: c 0924494

Ejemplo 1La clase Integer de Java contiene un método estático llamado toString, que aceptaun parámetro int y devuelve un objeto String. Se declara en Java de la siguienteforma:String Integer.toString(int)

Este método podría realizarse en el siguiente prototipo:D tostring PR O EXTPROC(*JAVA:D 'java.lang.Integer':D 'toString')D CLASS(*JAVA:'java.lang.String')D STATICD num 10I 0 VALUE

La palabra clave EXTPROC identifica el método como no generado por VARPG.También indica que el nombre del método es ’toString’, y que se encuentra en laclase ’java.lang.Integer’.

El O en la columna 40 y la palabra clave CLASS informan al compilador de que elmétodo devuelve un objeto, cuya clase es ’java.lang.String’.

La palabra clave STATIC indica que el método es estático, es decir, que no esnecesario un objeto Integer para invocar este método.

El tipo de datos del parámetro se especifica como 10I, que correlaciona al tipo dedatos Java int. Al ser el parámetro un int, debe pasarse por valor, y se precisa lapalabra clave VALUE.

Ejemplo 2La clase Integer de Java contiene un método estático llamado getInteger, que aceptaobjetos String e Integer como parámetros y devuelve un objeto Integer. En Java sedeclara de la siguiente forma:Integer Integer.getInteger(String, Integer)

Este método podría realizarse en el siguiente prototipo:D getint PR O EXTPROC(*JAVA:D 'java.lang.Integer':D 'getInteger')D CLASS(*JAVA:'java.lang.Integer')D STATICD string O CLASS(*JAVA:'java.lang.String')D num O CLASS(*JAVA:'java.lang.Integer')

Este método acepta dos objetos como parámetros. O está codificado en la columna40 de la especificación D y la palabra clave CLASS especifica la clase de cadaparámetro de objeto.

Ejemplo 3La clase Integer de Java contiene un método llamado shortValue, que devuelve larepresentación corta del objeto Integer utilizado para invocar el método. Se declaraen Java de la siguiente forma:short shortValue()

Este método podría realizarse en el siguiente prototipo:D shortval PR 5I 0 EXTPROC(*JAVA:D 'java.lang.Integer':D 'shortValue')

272 Programación con VisualAge RPG

Page 291: c 0924494

La palabra clave STATIC no se especifica porque el método no es estático. Elmétodo no utiliza parámetros, por lo que no se codifica ninguno.

El valor devuelto se especifica como 5I, que correlaciona al tipo de datos short deJava.

Ejemplo 4La clase Integer de Java contiene un método llamado equals, que acepta un objetocomo parámetro y devuelve un valor booleano. Se declara en Java de la siguienteforma:boolean equals(Object)

Este método podría realizarse en el siguiente prototipo:D equals PR N EXTPROC(*JAVA:D 'java.lang.Integer':D 'equals')D obj O CLASS(*JAVA:'java.lang.Object')

El valor devuelto se especifica como N, que correlaciona al tipo de datos booleande Java.

Cómo crear objetosSe precisa de un objeto para invocar un método no estático. La clase del objetodebe ser la misma que la clase que lo contiene. La creación de objetos o deinstancias de objeto se realiza invocando al constructor de la clase. El constructorde la clase no es un método estático, pero no requiere un objeto para llamarlo. Elnombre de método especial *CONSTRUCTOR se utiliza para realizar prototipos deconstructor.

Por ejemplo, para construir un objeto BigDecimal a partir de un valor float, elconstructor que espera un parámetro float debe invocarse:BigDecimal(float) devuelve un objeto BigDecimal

Este constructor podría realizarse en el siguiente prototipo:D bdcreate PR O EXTPROC(*JAVA:D 'java.math.BigDecimal':D *CONSTRUCTOR)D CLASS(*JAVA:'java.math.BigDecimal')D dnum 4F VALUE

Observe que el parámetro debe pasarse por valor porque correlaciona al tipo dedatos float de Java.

Cómo invocar métodos JavaLos métodos Java pueden invocarse utilizando códigos de operación CALLP(cuando no se espera un valor de retorno) y EVAL (cuando se espera un valor deretorno). No se necesita nueva sintaxis.

Al invocar un método estático, no se necesita un objeto para realizar la operación.Se precisa de un objeto para invocar un método no estático. El objeto que va autilizarse debe codificarse como el primer parámetro de la llamada. Este parámetrono se especifica en el prototipo, pero está implícito para todos los métodos noestáticos. Esto significa que cuando se invoca un método no estático, debeespecificarse al menos un parámetro.

Capítulo 18. Cómo invocar métodos Java desde programas VisualAge RPG 273

Page 292: c 0924494

Ejemplo 1

En este ejemplo, el objetivo es añadir dos valores BigDecimal. Para llevarlo a cabo,deben crearse instancias para dos objetos BigDecimal invocando el constructor parala clase BigDecimal, deben declararse los campos para el almacenamiento de losobjetos BigDecimal y debe invocarse el método add() en la clase BigDecimal.** Prototipo del constructor BigDecimal que acepta un parámetro* String. Devuelve un nuevo objeto BigDecimal.*

D bdcreate1 PR O EXTPROC(*JAVA:D 'java.math.BigDecimal':D *CONSTRUCTOR)D CLASS(*JAVA:'java.math.BigDecimal')D str O CLASS(*JAVA:'java.lang.String')** Prototipo del constructor BigDecimal que acepta un parámetro* doble. 8F correlaciona al tipo de datos double de Java y, por ello,* debe pasarse por VALUE. Devuelve un objeto BigDecimal.*

D bdcreate2 PR O EXTPROC(*JAVA:D 'java.math.BigDecimal':D *CONSTRUCTOR)D CLASS(*JAVA:'java.math.BigDecimal')D double 8F VALUE** Define los campos en los que almacenar los objetos BigDecimal.*

D bdnum1 S O CLASS(*JAVA:'java.math.BigDecimal')D bdnum2 S O CLASS(*JAVA:'java.math.BigDecimal')*

** Ya que uno de los constructores que estamos utilizando requiere un objeto String,* también necesitamos construir uno. Realice un prototipo del constructor* String que acepta una matriz de bytes como parámetro. Devuelve* un objeto String.*

D makestring PR O EXTPROC(*JAVA:D 'java.lang.String':D *CONSTRUCTOR)D CLASS(*JAVA:'java.lang.String')D bytes 10A** Define un campo en el que almacenar el objeto String.*

D string S O CLASS(*JAVA:'java.lang.String')** Prototipo del método add BigDecimal. Acepta un objeto BigDecimal* como parámetro y devuelve un objeto BigDecimal (la suma del parámetro* y del objeto BigDecimal utilizado para invocar).*

D add PR O EXTPROC(*JAVA:D 'java.lang.BigDecimal':D 'add')D CLASS(*JAVA:'java.math.BigDecimal')D bd1 O CLASS(*JAVA:'java.math.BigDecimal')** Define un campo en el que almacenar el resultado de la suma.*

D sum S O CLASS(*JAVA:'java.math.BigDecimal')DD double S 8F INZ(1.1)D fld1 S 10A

A continuación, el código que realiza la llamada.

274 Programación con VisualAge RPG

Page 293: c 0924494

C MOVEL 'mystring' fld1 10C*C* Invoca al constructor para la clase String, para crear un objetoC* String desde fld1. Al estar invocando al constructor, noC* necesitamos pasar un objeto String como primer parámetro.C*C EVAL string = makestring(fld1)C*C* Invoca al constructor BigDecimal que acepta un parámetro String,C* utilizando el objeto String para el que acabamos de crear una instancia.C*C EVAL bdnum1 = bdcreate1(string)C*C* Invoca al constructor BigDecimal que acepta doubleC* como parámetro.C*C EVAL bdnum2 = bdcreate2(double)C*C* Sume los dos objetos BigDecimal invocando el método add.C* El prototipo indica que add acepta un parámetro, peroC* al no ser add un método estático, también debemos pasarC* un objeto BigDecimal para realizar la llamada. Además debeC* pasarse como primer parámetro.C* bdnum1 es el objeto que estamos utilizando para invocarC* y bdnum2 es el parámetro.C*C EVAL sum = add(bdnum1:bdnum2)C* sum ahora contiene un objeto BigDecimal con el valorC* bdnum1 + bdnum2.

Ejemplo 2

Este ejemplo muestra cómo realizar un TRIM en Java utilizando el método trim()como alternativa a la función %TRIM incorporada en VARPG. El método trim() enla clase String no es un método estático, por lo que se necesita un objeto Stringpara invocarlo.** Define un campo en el que almacenar el objeto String que deseamos ajustar.*

D str S O CLASS(*JAVA:'java.lang.String')** Prototipo de constructor para la clase String. El* constructor espera una matriz de bytes.*

D makestring PR O EXTPROC(*JAVA:D 'java.lang.String':D *CONSTRUCTOR)D CLASS(*JAVA:'java.lang.String')D parm 10AD** Prototipo de método String getBytes que convierte un String en una matriz* de bytes. A partir de ahí, podremos almacenar esta matriz de bytes en un* campo alpha.*

D makealpha PR 10A EXTPROC(*JAVA:D 'java.lang.String':D 'getBytes')** Prototipo de método String trim. No necesita parámetros, pero* al no ser un método estático, debe invocarse utilizando un objeto* String.*

D trimstring PR O EXTPROC(*JAVA:D 'java.lang.String':

Capítulo 18. Cómo invocar métodos Java desde programas VisualAge RPG 275

Page 294: c 0924494

D 'trim')*

D fld S 10A INZ(' hello ')

La llamada se codifica de la forma siguiente:C*C* Invoca al constructor StringC*C EVAL str = makestring(fld)C*C* Ajusta la serie invocando el método String trim().C* Volveremos a utilizar el campo str para almacenar el resultado.C*C EVAL str = trimstring(str)C*C* Vuelve a convertir la serie en una matriz de bytes y la almacenaC* en fld.C*C EVAL fld = makealpha(str)

Los métodos estáticos se invocan de la misma forma, excepto que no se necesita unobjeto para realizar la llamada. Si el método makealpha() mostrado más arribafuese estático, la llamada sería:C EVAL fld = makealpha()

Si el método no devuelve un valor, utilice el código de operación CALLP.

Otras consideracionesEl compilador no intentará resolver las clases durante la compilación. Si una claseno puede localizarse durante el tiempo de ejecución, aparecerá un error deejecución. Éste indicará que se ha recibido un objeto UnresolvedLinkException delentorno Java.

El compilador no escribe las comprobaciones de parámetros durante lacompilación. Si se produce un conflicto entre el prototipo y el método que seinvoca, se recibirá un error durante la ejecución.

Es muy importante que se especifique *JAVARPG como primer parámetro deEXTPROC si el método invocado no ha sido generado por VARPG. En casocontrario, es posible que se produzca una de las dos situaciones de error descritasmás arriba.

276 Programación con VisualAge RPG

Page 295: c 0924494

Capítulo 19. Consideraciones al compilar para Java

Esta sección describe las restricciones de fuente de VARPG, posibles cambiosnecesarios en su fuente VARPG y diferencias de comportamiento del tiempo deejecución al utilizar la opción de construcción de Java para crear el fuente Java.

Convenio de denominación del archivo de proyectoEl nombre del archivo de proyecto para una aplicación Java debe ajustarse a losconvenios de denominación de Java. El primer carácter debe ser alfabético. Si elnombre de su proyecto no es correcto, puede utilizar el programa de utilidadRenombrar proyecto para renombrarlo. (Seleccione Renombrar proyecto del menúemergente en el icono del proyecto.)

Directivas de compilación condicionalEl compilador define dos directivas de compilación condicional para ayudar amantener un único archivo fuente que pueda utilizarse para crear tantocomponentes Windows como código fuente Java. Estas directivas son:v COMPILE_WINDOWS definida por el compilador cuando se solicita una

construcción de Windows.v COMPILE_JAVA definida por el compilador para una construcción Java.

El compilador define estos dos nombres, por lo que no es necesario definirlosmediante la directiva /DEFINE.

Restricciones del código fuente JavaLos siguientes elementos del lenguaje no están soportados cuando se generacódigo fuente Java:

Palabras clave:v ALIGNv EXPROPTSv STATIC en definiciones de campo. STATIC está soportado para

prototipos de métodos Java.

Códigos de operación:v ALLOCv CABxxv CALLBv DEALLOCv DSPLY (sólo para NOMAIN y EXE; en caso contrario, está soportado)v GOTOv REALLOCv TAG

Expansores de operación:v Mv R

Elementos del lenguaje:v SQL incorporado

Tipos de datos:v Tipo de datos de puntero

© Copyright IBM Corp. 1994, 2000 277

Page 296: c 0924494

Tipos de archivo:v SPECIAL

Operaciones con archivos:v Grabar registros por número de registro relativo

Cambios posibles en el código VARPGEsta sección resume los cambios que pueden ser necesarios en el fuente VARPGpara generar el código fuente Java.

1. La notación Desde/Hasta debe utilizarse al definir subcampos del PSDS eINFDS para permitir al compilador validar las definiciones de subcampo. Ladefinición de subcampos en INFDS e PSDS debe coincidir con las definicionesespecificadas en la publicación Language Reference de VARPG. Se emitirá unerror de tiempo de compilación si no coincide.

2. Una operación LEAVE o ITER incondicional debe ser la última de un bucle oel compilador Java emitirá un error. Si se da una operación LEAVE o ITERincondicional en un bucle, todas las operaciones que aparezcan después deella en el bucle deben eliminarse, ya que no se ejecutarían nunca.

3. Al añadir y sustraer duraciones de fecha/hora/indicación de hora, sólo debenutilizarse valores entre maxint (2.147.483.647) y -maxint (-2.147.483.648).

4. Debido a que Java no permite pasar por referencia a los valores int (10I), short(5I), float (4F) y double (8F), el código Java debe generarse en VARPG paramantener la posibilidad de convertir esta funcionalidad de subprocedimientosen Java. El código generado para conseguirlo puede provocar errores delcompilador java cuando el fuente VARPG contiene subprocedimientos conpuntos de retorno múltiples y recibe parámetros enteros o de coma flotantepasados por referencia.Ejemplo de código que podría provocar errores de compilación en Java:

C IF x = 1C ...C RETURN 1C ELSEC ...C RETURN 0C ENDIF

El código anterior debería cambiarse por:C IF x = 1C ...C RETURN 1C ELSEC ...C ENDIFC RETURN 0

5. Los caracteres ’*’, ’#’ y ’@’ no pueden utilizarse en identificadores Java.Debido a ello, todas las apariciones de ’*’, ’#’ y ’@’ en nombre VARPG deberácambiarse a ’_’. Es posible que esta conversión dé como resultado nombreduplicados.

6. Si una operación COMMIT o ROLBK está codificada en una aplicación quecarece de archivos, se emitirá un mensaje de gravedad 30 (RNF7833).

7. A causa de la forma en que un *PSSR local se convierte a Java, no es posibleinvocar un *PSSR local. Observe también que, al no soportarse GOTO, laúnica forma de dejar un *PSSR local y evitar el manejador por omisión escodificar una operación RETURN.

8. No hay posibilidad de cortocircuitar expresiones lógicas. Esto significa que nopuede preverse el orden en que se ejecutará una expresión lógica compuesta.

9. Los campos de longitud variable se implementan como una clase al convertira Java. Ello significa que no se almacenan como documentados en la

278 Programación con VisualAge RPG

Page 297: c 0924494

publicación VARPG Language Reference. El código que depende de que estoscampos se almacenen de una cierta forma no funcionará.

10. Los subcampos de estructura de datos no se inicializarán a espacios en blancosi no se provee de un valor inicial, pero se inicializarán a un valor poromisión dependiendo del tipo de datos del subcampo. El valor por omisión es0 para numéricos, espacios en blanco para carácter y *LOVAL para fecha, horae indicación de la hora. La longitud de los campos de longitud variable seestablecerá en 0.

11. Los valores *HIVAL y *LOVAL no se permiten en los campos de tipo gráfico yUCS-2.

12. Si se especifica una longitud para una estructura de datos, debe coincidir conla longitud total de los subcampos que contiene, en caso contrario elcompilador emitirá un mensaje de diagnóstico de gravedad 30.

13. Las subrutinas no pueden definirse en los subprocedimientos. La únicaexcepción a ello que un *PSSR puede definirse en un subproceso. Todas lassubrutinas contenidas en subprocedimientos deberían trasladarse fuera deellos. Si la subrutina accede a campos locales en el subprocedimiento, entonceslos campos deben convertirse en globales o bien la subrutina debe cambiarse aun subprocedimiento que acepte campos locales como parámetros.

14. Sentencias incondicionales LEAVE en bucles DO no se soportan. Se produciráun error del compilador Java si se da esta situación. Un LEAVE incondicionalen un bucle DO significa que el bucle se ejecutará una sola vez, por lo queLEAVE debería suprimirse y cambiarse el código para eliminar los códigos dela operación de bucle.

15. El uso de atributos de evento en instancias condicionales compuestasmodificadas provoca errores de compilación en Java. En su lugar, debierautilizarse la expresión libre equivalente.Ejemplo de código que podría provocar errores de compilación en Java:

C %mousex IFEQ xC %mousey ANDEQ yC ...C ENDIF

El código anterior debería cambiarse por:C IF %mousex = x ANDC %mousey = yC ...C ENDIF

16. Una operación RETURN incondicional no puede codificarse a menos que seala última instancia de una subrutina de usuario, una subrutina de acción o unsubprocedimiento. En caso contrario, el compilador Java puede informar deerrores.

17. Una operación LEAVESR incondicional no puede codificarse a menos que seala última sentencia de una subrutina de usuario o una subrutina de acción. Encaso contrario, el compilador Java puede informar de errores.

18. Las instancias SELECT pueden provocar errores del compilador Java cuandoaparecen en subprocedimientos, cuando contienen operaciones RETURN y nose ha codificado ningún RETURN en el cuerpo principal delsubprocedimiento.Ejemplo de código que podría provocar errores de compilación en Java:

C SELECTC x WHENEQ yC RETURN 1C x WHENEQ zC RETURN 2C OTHERC RETURN 0C ENDSL

Capítulo 19. Consideraciones al compilar para Java 279

Page 298: c 0924494

El código anterior debería cambiarse por:C SELECTC x WHENEQ yC RETURN 1C x WHENEQ zC RETURN 2C ENDSLC RETURN 0

En general, una operación RETURN debería codificarse para todas las posiblesvías de acceso de código de un subprocedimiento, en caso contrario, elcompilador Java emitirá errores.

19. Las matrices no pueden pasarse por valor a subprocedimientos.

Diferencias de tiempo de ejecuciónDebido a las diferencias entre los entornos Windows y Java, una aplicación puedeejecutarse de forma diferente en Java de lo que lo hace en Windows. Las siguientesáreas se ven afectadas:

1. La función incorporada %SCAN devolverá un resultado entero. En Windows,devuelve un resultado sin signo.

2. La opción de construcción de truncar valores numéricos no es fiable, por loque no debe dependerse de ella.

3. Cuando se produce una excepción de E/S, el usuario no dispondrá de laopción de volver a intentar la operación.

4. Las estructuras de datos no se tratan como un sólo campo largo de caracterescuando la aplicación Java se está ejecutando. Si se las utiliza como tales,pueden producirse resultados imprevistos.

5. El formato de los tipos de datos binarios, enteros y sin signo se trata de formadiferente para los archivos locales. Al leer y escribir archivos locales, sepresupone el formato Java, lo que significa que los bytes de mayor ordenestán situados más a la izquierda, mientras que en Windows están situadosmás a la derecha.

6. El tratamiento de excepciones para subprocedimientos tiene el mismocomportamiento que en las subrutinas de acción. Se invocará el gestor deerrores por omisión si la operación no tiene un *PSSR o INFSR local y no hayindicación de error.

7. Si al leer o escribir un campo en un archivo se encuentra un valor erróneo defecha, de hora o de indicación de la hora, el campo se establecerá en el valorpor omisión (*LOVAL). No se informará de ningún error.

8. Java sólo puede tratar una porción de milisegundos de 3 dígitos en lasindicaciones de la hora. Al realizar cálculos con indicaciones de la hora queutilizan 6 dígitos en la porción de milisegundos (es decir, que no expresan losmilisegundos mediante el formato 000xxx), los resultados pueden no ser losprevistos.

9. Los resultados intermedios de las expresiones no están limitados a 30 dígitos.De hecho, al procesar en el entorno VARPG, no se presta atención a laprecisión de los resultados intermedios.

10. No es posible compartir memoria entre componentes. Si un componente iniciaotro mediante START, los cambios realizados en parámetros pasados no sereflejan en los componentes.

11. No se informará del desbordamiento o subdesbordamiento de integer. Seinformará del desbordamiento o subdesbordamiento de float mediante elestado 9999.

12. Si se produce un error mientras se está ejecutando un subprocedimiento enuna aplicación NOMAIN o EXE, y no hay indicador de error o *PSSR,

280 Programación con VisualAge RPG

Page 299: c 0924494

entonces se informará del error al llamante y será éste el que se encargue deél. Cuando se procesa en Windows, la aplicación se interrumpirá.

13. Nunca se emitirá un error de estado 50 cuando se ejecuten aplicaciones Java.Java no proporciona mensajes de diagnóstico para las conversiones decaracteres que no puede manejar. Java puede emitir un estado 100 para unaconversión no satisfactoria o para una ArrayIndexOutOfBoundsExceptioncuando se utiliza la serie convertida.

14. El posicionamiento de un archivo de sistema principal en registros con valoresnulos cuando se ha especificado ALWNULL(*NO) da como resultadoCPF5035.

Restricciones de appletLos siguientes elementos del lenguaje no están soportados cuando se ejecuta unaapplet VARPG y dará como resultado errores de Java en tiempo de ejecución:v Archivos de impresorav Archivos localesv Llamadas a funciones C, subprocedimientos externo, archivos EXE.v Las aplicaciones NOMAIN y EXE no pueden ejecutarse como applets.

Problemas de impresión de J2SDK 1.2Actualmente, el Java 2 Software Development Kit (J2SDK), versión 1.2 o superior,parece tener problemas al enviar texto a un dispositivo de impresora. Una soluciónalternativa a este problema es ejecutar la aplicación Java de la siguiente forma:

java -Djava2d.font.usePlatformFont=true -ms32m -mx32m <classname>

Sin embargo, el texto impreso puede no ser exactamente como se esperaba. Esteproblema se resolverá cuando se arregle el problema con J2SDK 1.2, sin necesidadde actualizar VARPG.

Capítulo 19. Consideraciones al compilar para Java 281

Page 300: c 0924494

282 Programación con VisualAge RPG

Page 301: c 0924494

Capítulo 20. Llamada a funciones del sistema al compilar paraJava

El compilador de VisualAge RPG incluye soporte para la llamada a procedimientosexternos implementados como puntos de entrada de función en Bibliotecas deEnlace Dinámico (DLL) en la plataforma Windows a través de la Interfaz Nativa deJava (JNI). En esta sección se expone el modo de utilizar este soporte.

Debe consultar la sección Java Native Interface (JNI) de la documentación del Java2 Software Development Kit (J2SDK) como lectura de requisito previo.

Una llamada sencillaEl primer ejemplo de código muestra una llamada sencilla a un procedimientoexterno sin parámetros ni valor de retorno. La aplicación VisualAge RPG sencillallama a un procedimiento externo de una biblioteca de enlace dinámico sencilla. Laespecificación JNI dicta el nombre de función y la interfaz a la función nativa a laque debe llamarse. Se codificará una función y se compilará en una DLL nuevapara que sea el destino de la llamada. Los siguientes ejemplos sólo son unademostración de las funciones nativas codificadas en lenguaje C, aunque losprincipios de codificación que se ilustran también pueden aplicarse aimplementaciones de otros lenguajes. Una vez la función nativa tiene el control,tiene total libertad para llamar a otras funciones nativas como, por ejemplo las APIdel sistema.

Codifique un prototipo del procedimiento en VisualAge RPG, especificando lapalabra clave DLL para proporcionar el nombre de la DLL que contendrá lafunción nativa a la que debe llamarse. Puede codificarse opcionalmente la palabraclave EXTPROC para especificar un nombre de función distinto al nombre delprocedimiento en el programa VisualAge RPG.

Nota: El valor de la palabra clave EXTPROC es sensible a las mayúsculas yminúsculas. Codifique una llamada al procedimiento en el código fuente deVisualAge RPG.

© Copyright IBM Corp. 1994, 2000 283

Page 302: c 0924494

En la plataforma Windows, la función nativa se codifica de modo que utilice elenlace de programa StdCall. La función se codifica como función exportada en laDLL. El nombre de la función exportada debe coincidir con el nombre que dicta laespecificación JNI. El formato de la especificación JNI es el siguiente:Java_VARPGComponentName_ExternalProcedureName_OverloadedNativeMethods

Los nombres completos de las funciones nativas son ’Java_VCOMP1_proc1’ y’Java_VCOMP1_SUB2’ en este ejemplo. El método nativo sobrecargado no senecesita en este ejemplo.

La interfaz JNI dicta los dos primeros parámetros: un puntero a interfaz y unpuntero al objeto this. Los parámetros adicionales corresponden a los parámetrosdeclarados de los procedimientos. El archivo de cabecera jni.h se incluye en elprograma fuente de lenguaje C para proporcionar las definiciones de interfaz. Estearchivo lo proporciona J2SDK. Quizás deba actualizar la variable de entornoINCLUDE en el compilador C para que incluya el directorio que contiene losarchivos de cabecera de lenguaje C para J2SDK.

Por último, el archivo fuente C de ejemplo se compila en una DLL.

*********************************************************************** Archivo fuente: VCOMP1.VPG** Demostración de la llamada a un procedimiento externo mediante JNI.***********************************************************************

* Declarar un procedimiento llamado 'sub1' que hace referencia a* una función llamada 'proc1' de la DLL 'VSUB.DLL'

d sub1 pr dll('VSUB') extproc('proc1')

* Sin la palabra clave EXTPROCd sub2 pr dll('VSUB')

C *INZSR BEGSR

C callp sub1C callp sub2

c seton lr

C ENDSR

* Esta subrutina de acción se enlaza con un evento Create de la ventana.* Hace que el componente finalice tras ejecutar INZSR.

C CREATE1 BEGACTC seton LRC ENDACT

Figura 71. Archivo de ejemplo VCOMP1.VPG

284 Programación con VisualAge RPG

Page 303: c 0924494

Paso y recepción de parámetrosLa especificación JNI pasa directamente los tipos de datos primitivos de Java, peroVisualAge RPG procesa todos los tipos de datos de VARPG mediante clases. Estosignifica que las llamadas de VARPG a las funciones nativas siempre involucraránel paso de objetos. La especificación JNI proporciona funciones de interfaz para lafunción nativa, con el fin de acceder a los valores de los objetos pasados. Debido alos distintos métodos de clase que utiliza cada tipo de datos de VARPG, cada unode ellos se expondrá de forma individual.

Tipos de parámetro

CarácterVisualAge RPG implementa los campos de tipo carácter como matrices de bytes enJava, incluyendo un campo de tipo carácter de longitud uno. La funciónGetByteArrayElements de la interfaz JNI devuelve el valor del parámetro de matrizde bytes. Puede modificarse el valor y devolverlo a la función que efectúa lallamada mediante la función ReleaseByteArrayElements de la interfaz.

Nota: Tras llamar a la función de liberación no debe utilizarse el valor en lafunción nativa.

El primer parámetro de la función nativa del fuente de lenguaje C se ha cambiadode un puntero void a un puntero JNIEnv. Apunta a una tabla de punteros defunción para las funciones de la interfaz JNI. Los prototipos de los parámetros del

// Archivo fuente: VSUB.C

// Añadir (d:\jdk12\include;d:\jdk12\include\win32) al valor INCLUDE para// poder encontrar jni.h al compilar.

// Compilado con: IBM VisualAge(TM) para C++ para Windows(R), Versión 3.5// Mandato de compilación: icc /q /ss /ge- /fe vsub.dll vsub.c

#include <stdio.h>#include <string.h>

#include <jni.h>

//---------------------------------------------------------------

void _Export __stdcall Java_VCOMP1_proc1( void *je , void *jc)

{

printf(" llamada a proc1 satisfactoria.\n");}//---------------------------------------------------------------

void _Export __stdcall Java_VCOMP1_SUB2( void *je , void *jc){

printf(" llamada a SUB2 satisfactoria.\n");}

Figura 72. Archivo de ejemplo VSUB.C

Capítulo 20. Llamada a funciones del sistema al compilar para Java 285

Page 304: c 0924494

procedimiento externo se añaden a los parámetros de la función nativa, después delos dos punteros JNI estándares. Los parámetros de tipo carácter se declaran comotipos jbyteArray en la función nativa.

Se utiliza la función GetByteArrayElements de la interfaz para obtener el valor dela matriz de bytes Java para el campo de tipo carácter de VARPG.

Puede modificarse el valor obtenido y devolverse al llamador Java mediante lafunción ReleaseByteArrayElements de la interfaz.

Una vez liberado, no debe accederse al valor obtenido.

Nota: Es posible que el valor obtenido sea el valor real del objeto Java, no unacopia en memoria. Los cambios efectuados en él pueden reflejarse en elllamador Java aunque no se llame a la función de liberación. Consulte lafunción GetByteArrayElements en la documentación de JNI para obtenermás información.

286 Programación con VisualAge RPG

Page 305: c 0924494

*********************************************************************** Archivo fuente: VCOMP1.VPG** Demostración de la llamada a un procedimiento externo mediante JNI.***********************************************************************

* Declarar un procedimiento llamado 'sub1c' que hace referencia a* una función llamada 'proc1c' de la DLL 'VSUBC.DLL'

* Con 1 parámetro de tipo carácterd sub1c pr dll('VSUBC') extproc('proc1c')

d 1

* Sin la palabra clave EXTPROC* Con 2 parámetros de tipo carácter

d sub2c pr dll('VSUBC')d 4d 10

d c1 s 1 inz('J')d c4 s 4 inz('blue')d c10 s 10 inz('abcdefghij')

d mb1 m style(*info) button(*OK)

d rc s 9 0

C *INZSR BEGSR

C callp sub1c(c1)C callp sub2c(c4:c10)

* Visualizar los valores cambiados por las llamadasc c4 dsply mb1 rcc c10 dsply mb1 rc

c seton lrC ENDSR

* Esta subrutina de acción se enlaza con un evento Create de la ventana.* Hace que el componente finalice tras ejecutar INZSR.

C CREATE1 BEGACTC seton LRC ENDACT

Figura 73. Archivo de ejemplo VCOMPC.VPG

Capítulo 20. Llamada a funciones del sistema al compilar para Java 287

Page 306: c 0924494

// Archivo fuente: VSUBC.C// Función nativa con parámetros de tipo carácter

// Compilado con: IBM VisualAge(TM) para C++ para Windows(R), Versión 3.5// Mandato de compilación: icc /q /ss /ge- /fe vsubc.dll vsubc.c

#include <stdio.h>#include <string.h>

#include <jni.h>

//---------------------------------------------------------------

void _Export __stdcall Java_VCOMPC_proc1c( JNIEnv *je , void *jc,jbyteArray p1)

{char *c1;

printf(" llamada a proc1c satisfactoria.\n");

c1 = (char *) (*je)->GetByteArrayElements( je, p1, NULL);

printf(" c1 = \'%c\'\n", c1[0]);}//---------------------------------------------------------------

void _Export __stdcall Java_VCOMPC_SUB2C( JNIEnv *je , void *jc,jbyteArray p1, jbyteArray p2)

{char *c4;char *c10;

printf(" llamada a SUB2C satisfactoria.\n");

c4 = (char *) (*je)->GetByteArrayElements( je, p1, NULL);c10 = (char *) (*je)->GetByteArrayElements( je, p2, NULL);

printf(" c4 = %.4s.\n", c4);printf(" c10 = %.10s.\n", c10);

// Ahora cambiamos los valores

memcpy( c4, "Gray", 4);memcpy(c10, ">Received<", 10);

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, p1, (signed char *) c4, 0);(*je)->ReleaseByteArrayElements( je, p2, (signed char *) c10, 0);

}

Figura 74. Archivo de ejemplo VSUBC.C

288 Programación con VisualAge RPG

Page 307: c 0924494

Numérico con zona

*********************************************************************** Archivo fuente: VCOMPN.VPG** Demostración de la llamada a un procedimiento externo mediante JNI.***********************************************************************

* Con un parámetro Zoned(4,0)d subz pr dll('VSUBN')d 4S 0

* Con un parámetro Packed(9,2)d subp pr dll('VSUBN')

d 9P 2

* Con parámetros Binary(4,0), Binary(9,0)d subb pr dll('VSUBN')d 4B 0d 9B 0

d z4 s 4S 0 inz(1234)d p92 s 9P 2 inz(1234567.89)d b4 s 4B 0 inz(1234)d b9 s 9B 0 inz(123456789)

d mb1 m style(*info) button(*OK)d rc s 9 0

C *INZSR BEGSR

C callp subz(z4)C callp subp(p92)C callp subb(b4:b9)* Visualizar los valores cambiados por las llamadas

c z4 dsply mb1 rcc p92 dsply mb1 rc

c b4 dsply mb1 rcc b9 dsply mb1 rc

c seton lrC ENDSR

* Esta subrutina de acción se enlaza con un evento Create de la ventana.* Hace que el componente finalice tras ejecutar INZSR.

C CREATE1 BEGACTC seton LR

C ENDACT

Figura 75. Archivo de ejemplo VCOMPN.VPG

Capítulo 20. Llamada a funciones del sistema al compilar para Java 289

Page 308: c 0924494

// Archivo fuente: VSUBN.C

// Función nativa con parámetros de tipo carácter

// Añadir (d:\jdk12\include;d:\jdk12\include\win32) al valor INCLUDE para// poder encontrar jni.h al compilar.

// Compilado con: IBM VisualAge(TM) para C++ para Windows(R), Versión 3.5// Mandato de compilación: icc /q /ss /ge- /fe vsubn.dll vsubn.c

#include <stdio.h>#include <string.h>

#include <jni.h>

static void SwapBin2( short *b2);

static void SwapBin4( int *b4);

//---------------------------------------------------------------

void _Export __stdcall Java_VCOMPN_SUBZ( JNIEnv *je , void *jc,jobject p1)

{jclass cls;jmethodID mid;jobject aryobj;char *zd;

printf(" llamada a SUBZ satisfactoria.\n");

// p1: con zona// Llamar al método para obtener el valor con zona

cls = (*je)->GetObjectClass(je, p1);

mid = (*je)->GetMethodID( je, cls, "zonedValue", "()[B");

if ( mid == NULL){printf(" ERROR: GetMethod.\n");return;

}

aryobj = (*je)->CallObjectMethod( je, p1, mid);

zd = (char *) (*je)->GetByteArrayElements( je, aryobj, NULL);

printf(" zd = %.4s.\n", zd);

Figura 76. Archivo de ejemplo VSUBN.C (Pieza 1 de 2)

290 Programación con VisualAge RPG

Page 309: c 0924494

Como parámetro se pasa un objeto RpgZoned. Se utiliza el métodoRpgZoned::zonedValue para obtener una matriz de bytes que contiene el valornumérico del objeto en formato decimal con zona. Una vez se obtiene la matriz debytes en el lado Java de la interfaz, se llama a la función GetByteArrayElements dela interfaz JNI para acceder a la matriz de bytes en el lado nativo de la interfaz.

Para invocar el método zonedValue en el objeto, se utilizan las funcionesGetObjectClass, GetMethodID y CallObjectMethod de la interfaz. Debe tenersecuidado a la hora de especificar la firma de método correcta en la llamada aGetMethodID. (Sin parámetros, y sin devolver una matriz de bytes en este caso).

Para alterar el valor en el lado Java, se cambia el valor de la matriz de bytes, seinvoca la función ReleaseByteArrayElements de la interfaz para establecer elcambio efectuado en la matriz de bytes en el lado Java y se invoca en el lado Javael método de clase RpgZoned apropiado para establecer el valor del objetoRpgZoned en el valor representado por la matriz de bytes. En este caso, es elmétodo assignFromNative el que acepta una matriz de bytes y dos enteros comoparámetros. (La clase RpgNumeric cuya referencia se resuelve en el código deejemplo es una clase padre de la clase RpgZoned).

// Ahora cambiamos los valores

memcpy( zd, "9876", 4);

// Devolver el parámetro con zona

// 1. Actualizar el objeto matriz de bytes con el valor cambiado.

(*je)->ReleaseByteArrayElements( je, aryobj, (signed char *) zd, 0);

// 2. Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

// cls = (*je)->GetObjectClass(je, p1);// (clS) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

if ( mid == NULL){printf(" ERROR 2: GetMethod.\n");return;

}

(*je)->CallVoidMethod( je, p1, mid,aryobj,(int) 1, // = Component.ZONED_TYPE0 // precisión);

}

Figura 76. Archivo de ejemplo VSUBN.C (Pieza 2 de 2)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 291

Page 310: c 0924494

Numérico empaquetado

void _Export __stdcall Java_VCOMPN_SUBP( JNIEnv *je , void *jc,jobject p1) // P(9,2)

{jclass cls;jmethodID mid;jobject aryobj;char *packednum;

printf(" llamada a SUBP satisfactoria.\n");

// p1: empaquetado 9,2// Llamar al método para obtener el valor con zona

cls = (*je)->GetObjectClass(je, p1);

mid = (*je)->GetMethodID( je, cls, "packedValue", "()[B");

if ( mid == NULL){printf(" ERROR: GetMethod.\n");return;

}

aryobj = (*je)->CallObjectMethod( je, p1, mid);

packednum = (char *) (*je)->GetByteArrayElements( je, aryobj, NULL);

// Ahora cambiamos los valores

memcpy( packednum, "\x98\x76\x54\x32\x1C", 5);

Figura 77. Archivo de ejemplo VSUBN.C (continuación) (Pieza 1 de 2)

292 Programación con VisualAge RPG

Page 311: c 0924494

El caso de un parámetro de tipo decimal empaquetado es similar al de decimal conzona. Sólo se utilizan los métodos apropiados para convertir un objeto RpgPackeden un valor de matriz de bytes y viceversa.

Se utiliza el método RpgPacked::packedValue para obtener una matriz de bytesque contiene el valor numérico del objeto del parámetro RpgPacked en formatodecimal empaquetado nativo y, a continuación, se invocan las funciones de lainterfaz JNI para que la matriz de bytes java sea accesible desde el lado nativo dela interfaz.

Tras alterar la matriz de bytes en el lado nativo e invocar la funciónReleaseByteArrayElements de la interfaz para devolver la matriz de bytes al ladoJava, se vuelve a invocar el método assignFromNative para establecer el valor delobjeto RpgPacked en la matriz de bytes Java.

// Devolver el parámetro empaquetado

// 1. Actualizar el objeto matriz de bytes con el valor cambiado.

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,

// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, aryobj, (signed char *) packednum, 0);

// 2. Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

// cls = (*je)->GetObjectClass(je, p1);// (cls) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

if ( mid == NULL){printf(" ERROR 2: GetMethod.\n");return;

}

(*je)->CallVoidMethod( je, p1, mid,aryobj,(int) 2, // = Component.PACKED_TYPE2 // precisión (Núm. de pos. decimales));

}

Figura 77. Archivo de ejemplo VSUBN.C (continuación) (Pieza 2 de 2)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 293

Page 312: c 0924494

Binario

void _Export __stdcall Java_VCOMPN_SUBB( JNIEnv *je , void *jc,jobject p1 // B(4,0),jobject p2) // B(9,0)

{jclass cls;jmethodID mid;jobject aryobj;jobject aryobj2;

char *binarynum;char *b9;

short binary2;int binary4;

printf(" llamada a SUBB satisfactoria.\n");

// p1: binario 4,0

// Llamar al método para obtener el valor binario

cls = (*je)->GetObjectClass(je, p1);

mid = (*je)->GetMethodID( je, cls, "binaryValue", "()[B");

if ( mid == NULL){printf(" ERROR: GetMethod.\n");return;

}

aryobj = (*je)->CallObjectMethod( je, p1, mid);

binarynum = (char *) (*je)->GetByteArrayElements( je, aryobj, NULL);

// Debe invertirse el orden de bytes del valor recibido

memcpy( &binary2, binarynum, 2);

SwapBin2( &binary2);

printf(" binary = %hd\n", (short ) binary2);

// p2: binario 9,0// Llamar al método para obtener el valor binario

cls = (*je)->GetObjectClass(je, p2);

mid = (*je)->GetMethodID( je, cls, "binaryValue", "()[B");

if ( mid == NULL){printf(" ERROR: GetMethod.\n");return;

}

aryobj2 = (*je)->CallObjectMethod( je, p2, mid);

b9 = (char *) (*je)->GetByteArrayElements( je, aryobj2, NULL);

Figura 78. Archivo de ejemplo VSUBN.C (continuación) (Pieza 1 de 4)

294 Programación con VisualAge RPG

Page 313: c 0924494

// Debe invertirse el orden de bytes del valor recibido

memcpy( &binary4, b9, 4);SwapBin4( &binary4);

printf(" binary = %d.\n", (int ) binary4 );

// Ahora cambiamos los valores

binary2 = 5;

// Intercambiarlo de nuevo para devolver el valor Java

SwapBin2( &binary2);memcpy( binarynum, &binary2, 2);

// Devolver el parámetro

// 1. Actualizar el objeto matriz de bytes con el valor cambiado.

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, aryobj, (signed char *) binarynum, 0);

// 2. Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

cls = (*je)->GetObjectClass(je, p1);

// (cls) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

if ( mid == NULL){printf(" ERROR 2: GetMethod.\n");return;

}

(*je)->CallVoidMethod( je, p1, mid,aryobj,(int) 3, // = Component.BINARY_TYPE0 // precisión (Núm. de pos. decimales)

);

Figura 78. Archivo de ejemplo VSUBN.C (continuación) (Pieza 2 de 4)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 295

Page 314: c 0924494

// Ahora cambiamos los valores

binary4 = 19981999;

// Intercambiarlo de nuevo para devolver el valor Java

SwapBin4( &binary4);memcpy( b9, &binary4, 4);

// Devolver el parámetro

// 1. Actualizar el objeto matriz de bytes con el valor cambiado.

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, aryobj2, (signed char *) b9, 0);

// 2. Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

cls = (*je)->GetObjectClass(je, p2);// (cls) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

if ( mid == NULL){printf(" ERROR 2: GetMethod.\n");return;

}

(*je)->CallVoidMethod( je, p2, mid,aryobj2,(int) 3, // = Component.BINARY_TYPE0 // precisión (Núm. de pos. decimales));

}

Figura 78. Archivo de ejemplo VSUBN.C (continuación) (Pieza 3 de 4)

296 Programación con VisualAge RPG

Page 315: c 0924494

Este caso es similar al del decimal con zona. Sólo se utilizan los métodosapropiados para los objetos RpgBinary. La única complicación añadida es que laplataforma de la arquitectura Intel nativa almacena los enteros binarios en unformato ″bytes de menor orden a la izquierda″, mientras que el lado Java trabajacon un formato ″bytes de menor orden a la derecha″. Se emplean las funcionesSwapBin2 y SwapBin4 para invertir el orden de los bytes al convertir los enterosbinarios de dos y cuatro bytes de un lado al otro.

Se utiliza el método RpgBinary::binaryValue para obtener una matriz de bytes quecontiene el valor numérico del objeto del parámetro RpgBinary en formato binarionativo. A continuación, se invocan las funciones de la interfaz JNI para que lamatriz de bytes Java sea accesible desde el lado nativo de la interfaz. Tras alterar lamatriz de bytes en el lado nativo e invocar la función ReleaseByteArrayElementsde la interfaz para devolver la matriz de bytes al lado Java, se vuelve a invocar elmétodo assignFromNative para establecer el valor del objeto RpgBinary en lamatriz de bytes Java.

//-------------------------------------------------------------------static void SwapBin2( short *b2){

char tmp;char *p;

p = (char *) b2;

tmp = p[0];p[0] = p[1];p[1] = tmp;

}//-------------------------------------------------------------------static void SwapBin4( int *b4){

char tmp;char *p;

p = (char *) b4;

tmp = p[0];p[0] = p[3];p[3] = tmp;

tmp = p[1];p[1] = p[2];p[2] = tmp;

}

Figura 78. Archivo de ejemplo VSUBN.C (continuación) (Pieza 4 de 4)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 297

Page 316: c 0924494

Entero, sin signo

* Con parámetros: entero, sin signod subiu pr dll('VSUBO')d 5i 0d 10i 0d 5u 0d 10u 0

Figura 79. Ejemplo VJNIO.VPG

static void SwapBin2( char *);static void SwapBin4( char *);

void _Export __stdcall Java_VJNIO_SUBIU( JNIEnv *je , void *jc,jobject p1, jobject p2, jobject p3, jobject p4)

{jclass cls, cls2;jmethodID mid;jshort i2;jint i4;jobject aryobj3, aryobj4;unsigned short *u2;unsigned int *u4;

printf(" llamada a SUBIU satisfactoria.\n");

// p1: entero, 2 bytes// Llamar al método para obtener el valor

cls = (*je)->GetObjectClass(je, p1);mid = (*je)->GetMethodID( je, cls, "getValue", "()S");

if ( mid == NULL){

printf(" ERROR: GetMethod.\n");return;

}

i2 = (*je)->CallShortMethod( je, p1, mid);

printf(" i2 = %hd\n", (short) i2);

// p2: entero, 4 bytes// Llamar al método para obtener el valor

cls = (*je)->GetObjectClass(je, p2);

mid = (*je)->GetMethodID( je, cls, "getValue", "()I");

Figura 80. Ejemplo VSUBO.C (Pieza 1 de 6)

298 Programación con VisualAge RPG

Page 317: c 0924494

if ( mid == NULL){

printf(" ERROR: GetMethod.\n");return;

}

i4 = (*je)->CallIntMethod( je, p2, mid);

printf(" i4 = %d\n", (short) i4);

// p3: 2 bytes sin signo.// Llamar al método para obtener el valor doble

cls = (*je)->GetObjectClass(je, p3);

mid = (*je)->GetMethodID( je, cls, "unsignedValue", "()[B");

if ( mid == NULL){

printf(" ERROR: GetMethod.\n");

return;}

aryobj3 = (*je)->CallObjectMethod( je, p3, mid);

u2 = (unsigned short *) (*je)->GetByteArrayElements( je, aryobj3, NULL);

// Debe invertirse el orden de bytes del valor recibidoSwapBin2( (char *) u2);

printf(" u2 = %hu\n", *u2 );

Figura 80. Ejemplo VSUBO.C (Pieza 2 de 6)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 299

Page 318: c 0924494

// p4: 4 bytes sin signo.// Llamar al método para obtener el valor doble

cls = (*je)->GetObjectClass(je, p4);

mid = (*je)->GetMethodID( je, cls, "unsignedValue", "()[B");

if ( mid == NULL){

printf(" ERROR: GetMethod.\n");return;

}

aryobj4 = (*je)->CallObjectMethod( je, p4, mid);

u4 = (unsigned int *) (*je)->GetByteArrayElements( je, aryobj4, NULL);

// Debe invertirse el orden de bytes del valor recibidoSwapBin4( (char *) u4);

printf(" u4 = %u\n", *u4 );

// Ahora cambiamos los valores

i2 = 99;i4 = 88;*u2 = 77;*u4 = 66;

// Debe invertirse el orden de bytes del valor que se devuelveSwapBin2( (char *) u2);SwapBin4( (char *) u4);

// Devolver la memoria de la matriz a Java. Usada posteriormente// para establecer los valores de retorno de los parámetros

(*je)->ReleaseByteArrayElements( je, p3, (signed char *) u2, 0);(*je)->ReleaseByteArrayElements( je, p4, (signed char *) u4, 0);

Figura 80. Ejemplo VSUBO.C (Pieza 3 de 6)

300 Programación con VisualAge RPG

Page 319: c 0924494

// Devolver P1: entero 2 bytes

// Invocar el método RpgShortRef::setValue para establecer el valor del

// objeto en un valor de parámetro corto

// Obtener el ID de método para poder invocarlo.

cls = (*je)->GetObjectClass(je, p1);mid = (*je)->GetMethodID( je, cls, "setValue", "(S)V");

if ( mid == NULL){

printf(" ERROR 5: GetMethod.\n");return;

}

(*je)->CallVoidMethod( je, p1, mid, i2);

// Devolver P2: entero 4 bytes

// Invocar el método RpgIntRef::setValue para establecer el valor del

// objeto en un valor de parámetro entero

// Obtener el ID de método para poder invocarlo.

cls = (*je)->GetObjectClass(je, p2);mid = (*je)->GetMethodID( je, cls, "setValue", "(I)V");

if ( mid == NULL){

printf(" ERROR 6: GetMethod.\n");return;

}

(*je)->CallVoidMethod( je, p2, mid, i4);

Figura 80. Ejemplo VSUBO.C (Pieza 4 de 6)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 301

Page 320: c 0924494

// Devolver P3: 2 bytes sin signo

// Invocar el método RpgNumeric::assignFromNative para establecer

// el valor del objeto en un valor de parámetro sin signo

// Obtener el ID de método para poder invocarlo.cls = (*je)->GetObjectClass(je, p3);mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

if ( mid == NULL){

printf(" ERROR 7: GetMethod.\n");return;

}

// Pasar (aryobj3) como primer parámetro del método, ya que éste// espera un objeto de matriz de bytes Java

(*je)->CallVoidMethod( je, p3, mid,

aryobj3,(int) 5, // = Component.UNSIGNED_TYPE(int) 0); // 0 posiciones decimales

// Devolver P4: 4 bytes sin signo

// Invocar el método RpgNumeric::assignFromNative para establecer// el valor del objeto en un valor de parámetro sin signo

// Obtener el ID de método para poder invocarlo.

cls = (*je)->GetObjectClass(je, p4);

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

if ( mid == NULL){

printf(" ERROR 8: GetMethod.\n");return;

}

(*je)->CallVoidMethod( je, p4, mid, aryobj4,(int) 5, // = Component.UNSIGNED_TYPE(int) 0); // 0 posiciones decimales

}

Figura 80. Ejemplo VSUBO.C (Pieza 5 de 6)

302 Programación con VisualAge RPG

Page 321: c 0924494

Los enteros de 2 bytes utilizan los métodos RpgShortRef::getValue y setValue paraacceder a sus valores en valores cortos en el lado nativo. De forma similar, losenteros de 4 bytes utilizan los métodos RpgIntRef::getValue y setValue methodspara pasar valores enteros de lado nativo.

El paso de parámetros sin signo se complica por la falta de una primitiva Java quecoincida con un valor sin signo. Al valor del objeto sin signo se accede a través deprimitivas de matriz de bytes. El acceso al parámetro invoca el método paraobtener la matriz de bytes que representa el valor sin signo y, a continuación,invoca la función GetByteArrayElements de la interfaz para acceder a loselementos de la matriz en el lado nativo. Es más, en una plataformaIntel/Windows nativa, el valor del byte primero debe invertirse para convertirlo alformato ″bytes de orden bajo más a la izquierda″. Al devolver el parámetro sesigue un proceso inverso.

Flotante (4/8)

static void SwapBin2( char *p){

char tmp;

tmp = p[0];p[0] = p[1];

p[1] = tmp;}

static void SwapBin4( char *p){

char tmp;

tmp = p[0];p[0] = p[3];p[3] = tmp;

tmp = p[1];p[1] = p[2];p[2] = tmp;

}

Figura 80. Ejemplo VSUBO.C (Pieza 6 de 6)

* Con parámetros: flotante 4, flotante 8d subf pr dll('VSUBO')d 4fd 8f

Figura 81. Ejemplo VJNIO.VPG

Capítulo 20. Llamada a funciones del sistema al compilar para Java 303

Page 322: c 0924494

void _Export __stdcall Java_VJNIO_SUBF( JNIEnv *je , void *jc,jobject p1, jobject p2)

{jclass cls, cls2;jmethodID mid;jfloat f4;jdouble f8;

// p1: Flotante// Llamar al método para obtener el valor flotante

cls = (*je)->GetObjectClass(je, p1);mid = (*je)->GetMethodID( je, cls, "getValue", "()F");

if ( mid == NULL){

printf(" ERROR: GetMethod.\n");

return;}

f4 = (*je)->CallFloatMethod( je, p1, mid);

printf(" f4 = %f\n", (float) f4);

// p2: Doble// Llamar al método para obtener el valor doble

cls2 = (*je)->GetObjectClass(je, p2);

mid = (*je)->GetMethodID( je, cls2, "getValue", "()D");

if ( mid == NULL){

printf(" ERROR: GetMethod.\n");return;

}

f8 = (*je)->CallDoubleMethod( je, p2, mid);

printf(" f8 = %lf\n", (double) f8);

Figura 82. Ejemplo VSUBO.C (Pieza 1 de 2)

304 Programación con VisualAge RPG

Page 323: c 0924494

Los casos de parámetros flotante y doble son similares a los de los anteriores tiposde datos. Sólo los métodos para acceder a los valores del parámetro funcionan conlos tipos de datos primitivos de Java, que se correlacionan con las correspondientesprimitivas nativas, en lugar de las matrices de bytes habituales. Se utilizan lasfunciones de la interfaz JNI que trabajan con estas primitivas específicas parainvocar los métodos que sirven para acceder a los valores de los parámetros.

Se utilizan los métodos RpgFloatRef::getValue, setValue, RpgDoubleRef::getValue ysetValue.

// Ahora cambiamos los valores

f4 = 999.888;f8 = 98789.65456;

// Devolver el parámetro flotante

// Invocar el método desde la clase RpgFloatRef, que asigna// un valor de parámetro flotante al objeto

// Obtener el ID de método para poder invocarlo.

mid = (*je)->GetMethodID( je, cls, "setValue", "(F)V");

if ( mid == NULL){

printf(" ERROR 2: GetMethod.\n");

return;}

(*je)->CallVoidMethod( je, p1, mid, f4);

// Devolver el parámetro doble

// Invocar el método desde la clase RpgDoubleRef, que asigna// un valor de parámetro doble al objeto

// Obtener el ID de método para poder invocarlo.

mid = (*je)->GetMethodID( je, cls2, "setValue", "(D)V");

if ( mid == NULL){

printf(" ERROR 2: GetMethod.\n");return;

}

(*je)->CallVoidMethod( je, p2, mid, f8);}

Figura 82. Ejemplo VSUBO.C (Pieza 2 de 2)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 305

Page 324: c 0924494

Fecha, hora, indicación de la hora

Los parámetros de fecha, hora e indicación de la hora funcionan del mismo modoque los parámetros de tipo carácter, ya que en el lado Java se implementan comomatrices de bytes.

Paso de matricesEl manejo de matrices de parámetros se realiza de dos modos, en función del tipode datos. Debe invocarse la función GetObjectArrayElement de la interfaz paraobtener la dirección de un elemento de objeto individual de la matriz y, acontinuación, procesarlo del mismo modo que los métodos de parámetrosescalares. En el caso de una matriz de primitivas Java, existen funciones específicasde la interfaz para acceder a ellas como matrices de primitivas nativas y, a

* Con parámetros: fecha, hora, indicación de la horad subdtz pr dll('VSUBO')d 10dd 8td 26z

d fd s 10d inz(D'1999-12-31')d ft s 8t inz(T'09.00.00')d fts s 26z inz(Z'2001-01-01-08.01.01')

C callp subdtz(fd:ft:fts)

Figura 83. Ejemplo VJNIO.VPG

void _Export __stdcall Java_VJNIO_SUBDTZ( JNIEnv *je , void *jc,jbyteArray p1, jbyteArray p2, jbyteArray p3)

{char *fd, *ft, *fz;

fd = (char *) (*je)->GetByteArrayElements( je, p1, NULL);ft = (char *) (*je)->GetByteArrayElements( je, p2, NULL);fz = (char *) (*je)->GetByteArrayElements( je, p3, NULL);

printf(" fd = %.10s.\n", fd);printf(" ft = %.8s.\n", ft);printf(" fz = %.26s.\n", fz);

// Ahora cambiamos los valores

memcpy( fd, "2000-01-01",10);memcpy( ft, "17.00.00", 8);memcpy( fz, "2222-22-22-02.02.02", 19);

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, p1, (signed char *) fd, 0);(*je)->ReleaseByteArrayElements( je, p2, (signed char *) ft, 0);(*je)->ReleaseByteArrayElements( je, p3, (signed char *) fz, 0);

}

Figura 84. Ejemplo VSUBO.C

306 Programación con VisualAge RPG

Page 325: c 0924494

continuación, devolverlas a Java y liberarlas.

d subca pr dll('VSUBA')d 4d 10 dim(4)

d c1 s 1 inz('J')d c4 s 4 inz('blue')d c10 s 10 inz('abcdefghij') dim(4)

d subz pr dll('VSUBA')d 4S 0 dim(4)

d subp pr dll('VSUBA')

d 9P 2 dim(4)

d subb pr dll('VSUBA')d 4B 0 dim(4)d 9B 0 dim(4)

d z4 s 4S 0 dim(4)d p92 s 9P 2 dim(4)d b4 s 4B 0 dim(4)d b9 s 9B 0 dim(4)

d subf pr dll('VSUBA')

d 4f dim(4)d 8f dim(4)

Figura 85. Ejemplo VJNIA.VPG (Pieza 1 de 2)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 307

Page 326: c 0924494

d subdtz pr dll('VSUBA')d 10d dim(4)d 8t dim(4)d 26z dim(4)

d subiu pr dll('VSUBA')d 5i 0 dim(4)d 10i 0 dim(4)

d 5u 0 dim(4)d 10u 0 dim(4)

d f4 s 4f dim(4) inz(1234.56)d f8 s 8f dim(4) inz(1111.2222)d fd s 10d dim(4) inz(D'1999-12-31')d ft s 8t dim(4) inz(T'09.00.00')d fts s 26z dim(4) inz(Z'2001-01-01-08.01.01')

d fi2 s 5i 0 dim(4) inz(1)

d fi4 s 10i 0 dim(4) inz(2)d fu2 s 5u 0 dim(4) inz(3)d fu4 s 10u 0 dim(4) inz(4)

C *INZSR BEGSR

C callp subca(c4:c10)C callp subz(z4)C callp subp(p92)C callp subb(b4:b9)C callp subf(f4:f8)C callp subdtz(fd:ft:fts)

C callp subiu(fi2:fi4:fu2:fu4)c seton lrC ENDSR

Figura 85. Ejemplo VJNIA.VPG (Pieza 2 de 2)

308 Programación con VisualAge RPG

Page 327: c 0924494

// Archivo fuente: VSUBA.C// Función nativa con parámetros de tipo carácter// Añadir (d:\jdk12\include;d:\jdk12\include\win32) al valor INCLUDE para// poder encontrar jni.h al compilar.// Compilado con: IBM VisualAge(TM) para C++ para Windows(R), Versión 3.5// Mandato de compilación: icc /q /ss /ge- /fe vsuba.dll vsuba.c#include <stdio.h>#include <string.h>#include <jni.h>static void SwapBin2( char *);static void SwapBin4( char *);

void _Export __stdcall Java_VJNIA_SUBCA( JNIEnv *je , void *jc,

jbyteArray p1, jobjectArray p2){char *c4;char *c10;jobject p2e;

// Resolver el segundo elemento del parámetro de matrizp2e = (*je)->GetObjectArrayElement( je, p2,

1); /* Índ. matriz 1er elem. = 0. */

c4 = (char *) (*je)->GetByteArrayElements( je, p1, NULL);c10 = (char *) (*je)->GetByteArrayElements( je, p2e, NULL);

printf(" c4 = %.4s.\n", c4);

printf(" c10 = %.10s.\n", c10);

// Ahora cambiamos los valores

memcpy( c4, "Gray", 4);memcpy(c10, "Changed ", 10);

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseByteArrayElements( je, p1, (signed char *) c4, 0);(*je)->ReleaseByteArrayElements( je, p2e, (signed char *) c10, 0);

}

void _Export __stdcall Java_VJNIA_SUBZ( JNIEnv *je , void *jc,jobject p1)

Figura 86. Ejemplo VSUBA.C (Pieza 1 de 14)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 309

Page 328: c 0924494

{jclass cls;jmethodID mid;jobject aryobj;char *zd;jobject pe;

// Resolver el elemento del parámetro de matrizpe = (*je)->GetObjectArrayElement( je, p1,

0); /* Índ. matriz 1er elem. = 0. */

// p1: con zona// Llamar al método para obtener el valor con zona

cls = (*je)->GetObjectClass(je, pe);

mid = (*je)->GetMethodID( je, cls, "zonedValue", "()[B");

aryobj = (*je)->CallObjectMethod( je, pe, mid);

zd = (char *) (*je)->GetByteArrayElements( je, aryobj, NULL);

printf(" zd = %.4s.\n", zd);

// Ahora cambiamos los valores

memcpy( zd, "9876", 4);

// Devolver el parámetro con zona

// 1. Actualizar el objeto matriz de bytes con el valor cambiado.

(*je)->ReleaseByteArrayElements( je, aryobj, (signed char *) zd, 0);

Figura 86. Ejemplo VSUBA.C (Pieza 2 de 14)

310 Programación con VisualAge RPG

Page 329: c 0924494

// 2. Preparar la llamada al método desde la clase RpgNumeric que

// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

// cls = (*je)->GetObjectClass(je, p1);// (clS) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

(*je)->CallVoidMethod( je, pe, mid,aryobj,(int) 1, // = Component.ZONED_TYPE0 // precisión

);}

void _Export __stdcall Java_VJNIA_SUBP( JNIEnv *je , void *jc,jobject p1 // P(9,2))

{jclass cls;jmethodID mid;jobject aryobj;char *packednum;char tmp[80]; // Para rastreojobject pe;

// Resolver el elemento del parámetro de matriz

pe = (*je)->GetObjectArrayElement( je, p1,

1); /* Índ. matriz 1er elem. = 0. */

// p1: empaquetado 9,2// Llamar al método para obtener el valor con zona

cls = (*je)->GetObjectClass(je, pe);

mid = (*je)->GetMethodID( je, cls, "packedValue", "()[B");

aryobj = (*je)->CallObjectMethod( je, pe, mid);

packednum = (char *) (*je)->GetByteArrayElements( je, aryobj, NULL);

Figura 86. Ejemplo VSUBA.C (Pieza 3 de 14)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 311

Page 330: c 0924494

// Ahora cambiamos los valoresmemcpy( packednum, "\x98\x76\x54\x32\x1C", 5);

// Devolver el parámetro empaquetado

// 1. Actualizar el objeto matriz de bytes con el valor cambiado.

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, aryobj, (signed char *) packednum, 0);

// 2. Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al

// objeto RpgNumeric. Obtener el ID de método.

// cls = (*je)->GetObjectClass(je, p1);// (clS) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

(*je)->CallVoidMethod( je, pe, mid,aryobj,(int) 2, // = Component.PACKED_TYPE2 // precisión (Núm. de pos. decimales)

);}//---------------------------------------------------------------

Figura 86. Ejemplo VSUBA.C (Pieza 4 de 14)

312 Programación con VisualAge RPG

Page 331: c 0924494

void _Export __stdcall Java_VJNIA_SUBB( JNIEnv *je , void *jc,jobject p1 // B(4,0),jobject p2 // B(9,0))

{jclass cls;jmethodID mid;jobject aryobj;jobject aryobj2;char *binarynum;char *b9;

short binary2;int binary4;jobject pe,p2e;

// Resolver el elemento del parámetro de matriz

pe = (*je)->GetObjectArrayElement( je, p1,2); /* Índ. matriz 1er elem. = 0. */

// Resolver el elemento del parámetro de matriz

p2e = (*je)->GetObjectArrayElement( je, p2,3); /* Índ. matriz 1er elem. = 0. */

// p1: binario 4,0

// Llamar al método para obtener el valor binario

cls = (*je)->GetObjectClass(je, pe);

mid = (*je)->GetMethodID( je, cls, "binaryValue", "()[B");

aryobj = (*je)->CallObjectMethod( je, pe, mid);

binarynum = (char *) (*je)->GetByteArrayElements( je, aryobj, NULL);

Figura 86. Ejemplo VSUBA.C (Pieza 5 de 14)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 313

Page 332: c 0924494

// Debe invertirse el orden de bytes del valor recibido

memcpy( &binary2, binarynum, 2);SwapBin2( (char *) &binary2);

printf(" binary = %hd\n", (short ) binary2);

// p2: binario 9,0// Llamar al método para obtener el valor binario

cls = (*je)->GetObjectClass(je, p2e);

mid = (*je)->GetMethodID( je, cls, "binaryValue", "()[B");

aryobj2 = (*je)->CallObjectMethod( je, p2e, mid);

b9 = (char *) (*je)->GetByteArrayElements( je, aryobj2, NULL);

// Debe invertirse el orden de bytes del valor recibido

memcpy( &binary4, b9, 4);SwapBin4( (char *) &binary4);

printf(" binary = %d.\n", (int ) binary4 );

// Ahora cambiamos los valores

binary2 = 5;

// Intercambiarlo de nuevo para devolver el valor Java

SwapBin2( (char *) &binary2);

Figura 86. Ejemplo VSUBA.C (Pieza 6 de 14)

314 Programación con VisualAge RPG

Page 333: c 0924494

memcpy( binarynum, &binary2, 2);

// Devolver el parámetro empaquetado

// 1. Actualizar el objeto matriz de bytes con el valor cambiado.

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,

// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, aryobj, (signed char *) binarynum, 0);

// 2. Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

cls = (*je)->GetObjectClass(je, pe);// (clS) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

(*je)->CallVoidMethod( je, pe, mid,aryobj,(int) 3, // = Component.BINARY_TYPE0 // precisión (Núm. de pos. decimales)

);

// Ahora cambiamos los valores

binary4 = 19981999;

// Intercambiarlo de nuevo para devolver el valor Java

SwapBin4( (char *) &binary4);

memcpy( b9, &binary4, 4);

Figura 86. Ejemplo VSUBA.C (Pieza 7 de 14)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 315

Page 334: c 0924494

// Devolver el parámetro empaquetado

// 1. Actualizar el objeto matriz de bytes con el valor cambiado.

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, aryobj2, (signed char *) b9, 0);

// 2. Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al

// objeto RpgNumeric. Obtener el ID de método.

cls = (*je)->GetObjectClass(je, p2e);// (clS) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

(*je)->CallVoidMethod( je, p2e, mid,aryobj2,(int) 3, // = Component.BINARY_TYPE0 // precisión (Núm. de pos. decimales)

);}

//---------------------------------------------------------------

Figura 86. Ejemplo VSUBA.C (Pieza 8 de 14)

316 Programación con VisualAge RPG

Page 335: c 0924494

void _Export __stdcall Java_VJNIA_SUBF( JNIEnv *je , void *jc,jfloatArray p1, jdoubleArray p2)

{jclass cls, cls2;jmethodID mid;jfloat *f4;jdouble *f8;jobject p1e,p2e;

printf(" llamada a SUBF satisfactoria.\n");

f4 = (*je)->GetFloatArrayElements( je, p1, NULL);

f8 = (*je)->GetDoubleArrayElements( je, p2, NULL);

printf(" f4 = %f\n", (float) f4[0]);

// p2: Doble// Llamar al método para obtener el valor doble

printf(" f8 = %lf\n", (double) f8[0]);

// Ahora cambiamos los valores

f4[0] = 999.888;f8[1] = 98789.65456;

// Devolver el parámetro flotante

(*je)->ReleaseFloatArrayElements( je, p1, f4, 0);(*je)->ReleaseDoubleArrayElements( je, p2, f8, 0);

}

Figura 86. Ejemplo VSUBA.C (Pieza 9 de 14)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 317

Page 336: c 0924494

//---------------------------------------------------------------

void _Export __stdcall Java_VJNIA_SUBDTZ( JNIEnv *je , void *jc,jbyteArray p1, jbyteArray p2, jbyteArray p3)

{char *fd, *ft, *fz;jobject p1e, p2e, p3e;

printf(" llamada a SUBDTZ satisfactoria.\n");

// Resolver el elemento del parámetro de matriz

p1e = (*je)->GetObjectArrayElement( je, p1,2); /* Índ. matriz 1er elem. = 0. */

p2e = (*je)->GetObjectArrayElement( je, p2,3); /* Índ. matriz 1er elem. = 0. */

p3e = (*je)->GetObjectArrayElement( je, p3,0); /* Índ. matriz 1er elem. = 0. */

fd = (char *) (*je)->GetByteArrayElements( je, p1e, NULL);ft = (char *) (*je)->GetByteArrayElements( je, p2e, NULL);fz = (char *) (*je)->GetByteArrayElements( je, p3e, NULL);

printf(" fd = %.10s.\n", fd);printf(" ft = %.8s.\n", ft);printf(" fz = %.26s.\n", fz);

// Ahora cambiamos los valores

memcpy( fd, "2000-01-01",10);memcpy( ft, "17.00.00", 8);memcpy( fz, "2222-22-22-02.02.02", 19);

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseByteArrayElements( je, p1e, (signed char *) fd, 0);(*je)->ReleaseByteArrayElements( je, p2e, (signed char *) ft, 0);(*je)->ReleaseByteArrayElements( je, p3e, (signed char *) fz, 0);

}

Figura 86. Ejemplo VSUBA.C (Pieza 10 de 14)

318 Programación con VisualAge RPG

Page 337: c 0924494

//---------------------------------------------------------------

void _Export __stdcall Java_VJNIA_SUBIU( JNIEnv *je , void *jc,jshortArray p1, jintArray p2, jobject p3, jobject p4)

{jclass cls, cls2;jmethodID mid;jshort *i2;jint *i4;jobject aryobj3, aryobj4;unsigned short *u2;unsigned int *u4;jobject p1e, p2e, p3e, p4e;

printf(" llamada a SUBIU satisfactoria.\n");

// Resolver el elemento del parámetro de matriz

i2 = (*je)->GetShortArrayElements( je, p1, NULL);i4 = (*je)->GetIntArrayElements( je, p2, NULL);

p3e = (*je)->GetObjectArrayElement( je, p3, 2);p4e = (*je)->GetObjectArrayElement( je, p4, 3);

printf(" i2 = %hd\n", (short) i2[0]);

printf(" i4 = %d\n", (short) i4[1]);

// p3: 2 bytes sin signo.// Llamar al método para obtener el valor doble

cls = (*je)->GetObjectClass(je, p3e);

mid = (*je)->GetMethodID( je, cls, "unsignedValue", "()[B");

aryobj3 = (*je)->CallObjectMethod( je, p3e, mid);

u2 = (unsigned short *) (*je)->GetByteArrayElements( je, aryobj3, NULL);

Figura 86. Ejemplo VSUBA.C (Pieza 11 de 14)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 319

Page 338: c 0924494

// Debe invertirse el orden de bytes del valor recibidoSwapBin2( (char *) u2);

printf(" u2 = %hu\n", *u2 );

// p4: 4 bytes sin signo.// Llamar al método para obtener el valor doble

cls = (*je)->GetObjectClass(je, p4e);

mid = (*je)->GetMethodID( je, cls, "unsignedValue", "()[B");

aryobj4 = (*je)->CallObjectMethod( je, p4e, mid);

u4 = (unsigned int *) (*je)->GetByteArrayElements( je, aryobj4, NULL);

// Debe invertirse el orden de bytes del valor recibidoSwapBin4( (char *) u4);

printf(" u4 = %u\n", *u4 );

Figura 86. Ejemplo VSUBA.C (Pieza 12 de 14)

320 Programación con VisualAge RPG

Page 339: c 0924494

// Ahora cambiamos los valores

i2[0] = 99;i4[1] = 88;

*u2 = 77;*u4 = 66;

// Debe invertirse el orden de bytes del valor que se devuelveSwapBin2( (char *) u2);SwapBin4( (char *) u4);

// Devolver la memoria de la matriz a Java. Usada posteriormente// para establecer los valores de retorno de los parámetros

(*je)->ReleaseByteArrayElements( je, p3e, (signed char *) u2, 0);(*je)->ReleaseByteArrayElements( je, p4e, (signed char *) u4, 0);

(*je)->ReleaseShortArrayElements( je, p1, i2, 0);

(*je)->ReleaseIntArrayElements( je, p2, i4, 0);

// Devolver P3: 2 bytes sin signo

// Invocar el método RpgNumeric::assignFromNative para establecer// el valor del objeto en un valor de parámetro sin signo

// Obtener el ID de método para poder invocarlo.cls = (*je)->GetObjectClass(je, p3e);mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

// Pasar (aryobj3) como primer parámetro del método, ya que éste

// espera un objeto de matriz de bytes Java

(*je)->CallVoidMethod( je, p3e, mid,aryobj3,(int) 5, // = Component.UNSIGNED_TYPE(int) 0); // 0 posiciones decimales

Figura 86. Ejemplo VSUBA.C (Pieza 13 de 14)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 321

Page 340: c 0924494

Devolución de un valor de tipo carácter

// Devolver P4: 4 bytes sin signo

// Invocar el método RpgNumeric::assignFromNative para establecer// el valor del objeto en un valor de parámetro sin signo

// Obtener el ID de método para poder invocarlo.

cls = (*je)->GetObjectClass(je, p4e);mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

(*je)->CallVoidMethod( je, p4e, mid, aryobj4,(int) 5, // = Component.UNSIGNED_TYPE(int) 0); // 0 posiciones decimales

}

static void SwapBin2( char *p){

char tmp;

tmp = p[0];p[0] = p[1];p[1] = tmp;

}

static void SwapBin4( char *p)

{char tmp;

tmp = p[0];p[0] = p[3];p[3] = tmp;

tmp = p[1];p[1] = p[2];p[2] = tmp;

}

Figura 86. Ejemplo VSUBA.C (Pieza 14 de 14)

d subrc pr 10 dll('VSUBR')

d fc s 10 inz('ibm varpg ')

C eval fc = subrc

Figura 87. Ejemplo VJNIR.VPG

322 Programación con VisualAge RPG

Page 341: c 0924494

La devolución de un valor desde la función implica la obtención del objeto Javaapropiado y, después, devolverlo. En este ejemplo, se crea un objeto nuevo (quecoincide con un campo Character(10)) y, a continuación, se asigna su valor. Ya quelos campos de tipo carácter de RPG se implementan como matrices de bytes Java,se crea un objeto de matriz de bytes Java con una longitud de 10, luego se utilizala función GetByteArrayElements de la interfaz para acceder a los elementos de lamatriz de bytes en el lado nativo, después se liberan y se devuelven a Java y, porúltimo, se utilizan para devolverlo desde la función.

Si el objeto de matriz de bytes Java apropiado ya estaba disponible en uno de losparámetros de entrada, podría haberse utilizado éste en lugar de crear un objetonuevo.

Devolución de un valor de tipo decimal con zona

jbyteArray _Export __stdcall Java_VJNIR_SUBRC( JNIEnv *je , void *jc){jbyteArray ba;char *p;

printf(" llamada a SUBRC satisfactoria.\n");

// Crear un nuevo objeto de matriz de bytes para poder devolverlo.

ba = (*je)->NewByteArray( je, 10 /* = longitud matriz bytes */ );

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "Satisfactorio ",10);

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

return ba;}

Figura 88. Ejemplo VSUBR.C

d subrs pr 5s 0 dll('VSUBR')d fs s 5s 0

C eval fc = subrc

Figura 89. Ejemplo VJNIR.VPG

Capítulo 20. Llamada a funciones del sistema al compilar para Java 323

Page 342: c 0924494

jobject _Export __stdcall Java_VJNIR_SUBRS( JNIEnv *je , void *jc){jclass cls;jmethodID mid;jobject rzo;

jbyteArray ba;char *p;

printf(" llamada a SUBRS satisfactoria.\n");

// Crear un nuevo objeto RpgZoned.

cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgZoned");

mid = (*je)->GetMethodID( je, cls, "<init>", "(II)V");

rzo = (*je)->NewObject( je, cls, mid,(int) 5, /* núm. de dígitos */

(int) 0 /* núm. de posiciones decimales */);

// Para establecer el valor del objeto decimal con zona, necesitamos// una matriz de bytes Java para utilizarla como parámetro de entrada// del método para establecer el objeto decimal con zona.// Puede construirse un objeto de matriz de bytes nuevo u obtener uno// recuperando el valor decimal con zona del objeto.

// Construir una matriz de bytes.

// Crear un objeto de matriz de bytes nuevo

ba = (*je)->NewByteArray( je, 5 /* = longitud matriz bytes */ );

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "55555", 5);

Figura 90. Ejemplo VSUBR.C (Pieza 1 de 2)

324 Programación con VisualAge RPG

Page 343: c 0924494

Se construye un objeto RpgZoned para poder devolverlo. A continuación, seestablece su valor mediante una llamada a método. Sin embargo, el método paraestablecer el valor necesita un objeto de matriz de bytes como parámetro deentrada que suministre el valor, por lo que primero se construye el objeto dematriz de bytes.

El objeto RpgZoned se construye averiguando la clase, a continuación, el métodoconstructor de la clase y, por último invocando el método constructor. Acontinuación se construye un objeto de matriz de bytes y se establece en un valorde bytes con formato decimal con zona. Luego se resuelve un método paraestablecer el valor del objeto RpgZoned y se invoca, pasándole el objeto de matrizde bytes como uno de sus parámetros.

Devolución de un valor de tipo empaquetado

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

// Preparar la llamada al método desde la clase RpgNumeric que

// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

// cls = (*je)->GetObjectClass(je, p1);// (cls) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

(*je)->CallVoidMethod( je, rzo, mid,ba,(int) 1, // = Component.ZONED_TYPE0 // precisión

);return rzo;

}

Figura 90. Ejemplo VSUBR.C (Pieza 2 de 2)

d subrp pr 5p 0 dll('VSUBR')d fp s 5p 0

C eval fp = subrp

Figura 91. Ejemplo VJNIR.VPG

Capítulo 20. Llamada a funciones del sistema al compilar para Java 325

Page 344: c 0924494

jobject _Export __stdcall Java_VJNIR_SUBRP( JNIEnv *je , void *jc){jclass cls;jmethodID mid;jobject ro;

jbyteArray ba;char *p;

printf(" llamada a SUBRP satisfactoria.\n");

// Crear un nuevo objeto RpgPacked.

cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgPacked");

mid = (*je)->GetMethodID( je, cls, "<init>", "(II)V");

ro = (*je)->NewObject( je, cls, mid,(int) 5, /* núm. de dígitos */

(int) 0 /* núm. de posiciones decimales */);

// Para establecer el valor del objeto decimal empaquetado, necesitamos// una matriz de bytes Java para utilizarla como parámetro de entrada// del método para establecer el objeto decimal empaquetado.// Puede construirse un objeto de matriz de bytes nuevo u obtener uno// recuperando el valor decimal empaquetado del objeto.

// Crear un objeto de matriz de bytes nuevo

ba = (*je)->NewByteArray( je, 3 /* = longitud matriz bytes */ );

Figura 92. Ejemplo VSUBR.C (Pieza 1 de 2)

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "\x55\x55\x5C", 3);

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

// Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

(*je)->CallVoidMethod( je, ro, mid,ba, // El objeto de matriz de bytes(int) 2, // = Component.PACKED_TYPE0 // posiciones decimales

);return ro;

}

Figura 92. Ejemplo VSUBR.C (Pieza 2 de 2)

326 Programación con VisualAge RPG

Page 345: c 0924494

La devolución de un valor decimal empaquetado es similar al caso de un valordecimal con zona ilustrado más arriba.

El objeto RpgPacked se construye averiguando la clase, a continuación, el métodoconstructor de la clase y, por último invocando el método constructor. Acontinuación se construye un objeto de matriz de bytes y se establece en un valorde bytes con formato decimal empaquetado. Luego se resuelve un método paraestablecer el valor del objeto RpgPacked y se invoca, pasándole el objeto de matrizde bytes como uno de sus parámetros.

Devolución de un valor de tipo binario

d subrb pr 5b 0 dll('VSUBR')d fb s 5b 0

C eval fb = subrb

Figura 93. Ejemplo VJNIR.VPG

jobject _Export __stdcall Java_VJNIR_SUBRB( JNIEnv *je , void *jc){jclass cls;jmethodID mid;jobject ro;

jbyteArray ba;char *p;

printf(" llamada a SUBRB satisfactoria.\n");

// Crear un nuevo objeto RpgPacked.

cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgBinary");

mid = (*je)->GetMethodID( je, cls, "<init>", "(II)V");

ro = (*je)->NewObject( je, cls, mid,(int) 5, /* núm. de dígitos */

(int) 0 /* núm. de posiciones decimales */);

Figura 94. Ejemplo VSUBR.C (Pieza 1 de 2)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 327

Page 346: c 0924494

La devolución de un valor binario es similar a la de los casos anteriores para losdecimales con zona y empaquetados, sólo que se devuelve un objeto RpgBinary.

Devolución de un valor de tipo entero

// Para establecer el valor del objeto, necesitamos// una matriz de bytes Java para utilizarla como parámetro de entrada// del método para establecer el objeto.

// Crear un objeto de matriz de bytes nuevo

ba = (*je)->NewByteArray( je, 4 /* = longitud matriz bytes */ );

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "\x00\x00\xD9\x03", 4); // 55555 = 0xD903

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

// Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

(*je)->CallVoidMethod( je, ro, mid,ba, // El objeto de matriz de bytes(int) 3, // = Component.Binary_TYPE0 // posiciones decimales

);return ro;

}

Figura 94. Ejemplo VSUBR.C (Pieza 2 de 2)

d subri2 pr 5i 0 dll('VSUBR')d subri4 pr 10i 0 dll('VSUBR')

d fi2 s 5i 0d fi4 s 10i 0

C eval fi2= subri2C eval fi4= subri4

Figura 95. Ejemplo VJNIR.VPG

328 Programación con VisualAge RPG

Page 347: c 0924494

La devolución de un valor entero binario de 2 o 4 bytes es sencilla. Esto se debe aque los tipos se soportan como primitivas Java.

Devolución de un valor entero sin signo

jshort _Export __stdcall Java_VJNIR_SUBRI2( JNIEnv *je , void *jc){jshort rc;rc = -5555;return rc;

}

jint _Export __stdcall Java_VJNIR_SUBRI4( JNIEnv *je , void *jc){return -55555;

}

Figura 96. Ejemplo VSUBR.C

d subru pr 10u 0 dll('VSUBR')d fu s 10u 0C eval fu = subru

Figura 97. Ejemplo VJNIR.VPG

Capítulo 20. Llamada a funciones del sistema al compilar para Java 329

Page 348: c 0924494

jobject _Export __stdcall Java_VJNIR_SUBRU( JNIEnv *je , void *jc){jclass cls;jmethodID mid;jobject ro;

jbyteArray ba;char *p;

printf(" llamada a SUBRU satisfactoria.\n");

// Crear un nuevo objeto RpgUnsigned.

cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgUnsigned");

mid = (*je)->GetMethodID( je, cls, "<init>", "(II)V");

ro = (*je)->NewObject( je, cls, mid,(int) 5, /* núm. de dígitos */

(int) 0 /* núm. de posiciones decimales */);

// Para establecer el valor del objeto, necesitamos// una matriz de bytes Java para utilizarla como parámetro de entrada// del método para establecer el objeto.

// Crear un objeto de matriz de bytes nuevo

ba = (*je)->NewByteArray( je, 4 /* = longitud matriz bytes */ );

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "\x00\x00\xD9\x03", 4); // 55555 = 0xD903

Figura 98. Ejemplo VSUBR.C (Pieza 1 de 2)

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

// Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

(*je)->CallVoidMethod( je, ro, mid,ba, // El objeto de matriz de bytes(int) 5, // = Component.UNSIGNED_TYPE0 // posiciones decimales

);return ro;

}

Figura 98. Ejemplo VSUBR.C (Pieza 2 de 2)

330 Programación con VisualAge RPG

Page 349: c 0924494

La devolución de un valor binario sin signo es similar a la de los casos anteriorespara los decimales con zona y empaquetados, sólo que se utiliza un objetoRpgUnsigned.

Devolución de un valor de fecha, hora o indicación de la hora

Los valores de fecha, hora e indicación de la hora se devuelven como matrices debytes Java con la longitud esperada. Es similar a los datos de tipo carácter.

Devolución de un valor de tipo flotante

d subrd pr 10d dll('VSUBR')d fd s 10dC eval fd = subrd

Figura 99. Ejemplo VJNIR.VPG

jbyteArray _Export __stdcall Java_VJNIR_SUBRD( JNIEnv *je , void *jc){jbyteArray ba;char *p;

// Crear un nuevo objeto de matriz de bytes para poder devolverlo.

ba = (*je)->NewByteArray( je, 10 /* = longitud matriz bytes */ );

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "2000-01-01",10);

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

return ba;}

Figura 100. Ejemplo VSUBR.C

d subrf pr 4f dll('VSUBR')d subrf8 pr 8f dll('VSUBR')d ff s 4fd ff8 s 8f

C eval ff = subrfC eval ff8= subrf8

Figura 101. Ejemplo VJNIR.VPG

Capítulo 20. Llamada a funciones del sistema al compilar para Java 331

Page 350: c 0924494

La devolución de un valor de tipo flotante o doble (flotante de 8 bytes) se realizadirectamente. Esto se debe a que los tipos se soportan como primitivas Java.

Devolución de un valor de tipo carácter de longitud variable

Un valor de tipo carácter de longitud variable se devuelve mediante una matriz debytes Java, en la que la longitud de la matriz coincide con la longitud del valoractual.

jfloat _Export __stdcall Java_VJNIR_SUBRF( JNIEnv *je , void *jc){jfloat rc;

rc = -4444.4444;return rc;

}

jdouble _Export __stdcall Java_VJNIR_SUBRF8( JNIEnv *je , void *jc){return -7777777.55555;

}

Figura 102. Ejemplo VSUBR.C

d subrcv pr 10 dll('VSUBR') varyingd fcv s 10 varyingC eval fcv= subrcv

Figura 103. Ejemplo VJNIR.VPG

jbyteArray _Export __stdcall Java_VJNIR_SUBRCV( JNIEnv *je , void *jc){jbyteArray ba;char *p;

// Devolver una matriz de bytes de la longitud de datos actual

// Crear un nuevo objeto de matriz de bytes para poder devolverlo.

ba = (*je)->NewByteArray( je, 4 /* = longitud matriz bytes */ );

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "abcd",4);

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

return ba;}

Figura 104. Ejemplo VSUBR.C

332 Programación con VisualAge RPG

Page 351: c 0924494

Devolución de valores de matrizSe llama a una función de la interfaz JNI para asignar un objeto de matriz. Si loselementos de la matriz son tipos de datos primitivos de Java, se utilizan lasfunciones de la interfaz para asignar estos tipos de objetos de matriz. (Existe unafunción específica para cada tipo primitivo). También asignan los elementos de lamatriz. A continuación, sólo se trata de llamar a la función de la interfaz paracorrelacionar los elementos de la matriz con la memoria nativa y ya se puedenestablecer, liberar y devolver a Java y, a continuación, devolverlos desde la función.

Si los elementos de la matriz no son de tipos primitivos de Java, entonces debeasignarse un objeto Java para cada elemento de la matriz, establecer su valor segúnse desee y, por último, asignar el objeto al elemento específico de la matriz. Laasignación de los objetos individuales para los elementos es similar al caso delvalor de retorno escalar para dicho tipo de datos.

* Archivo fuente: VJNIRA.VPG

d subrca pr 10 dll('VSUBRA') dim(4)d subrsa pr 5s 0 dll('VSUBRA') dim(4)d subrpa pr 5p 0 dll('VSUBRA') dim(4)d subrba pr 5b 0 dll('VSUBRA') dim(4)d subri2a pr 5i 0 dll('VSUBRA') dim(4)d subri4a pr 10i 0 dll('VSUBRA') dim(4)d subrua pr 10u 0 dll('VSUBRA') dim(4)

d subrda pr 10d dll('VSUBRA') dim(4)d subrfa pr 4f dll('VSUBRA') dim(4)d subrf8a pr 8f dll('VSUBRA') dim(4)d subrcva pr 10 dll('VSUBRA') varying dim(4)

d fc s 10 dim(4)d fs s 5s 0 dim(4)d fp s 5p 0 dim(4)d fb s 5b 0 dim(4)

d fi2 s 5i 0 dim(4)d fi4 s 10i 0 dim(4)d fu s 10u 0 dim(4)d fd s 10d dim(4)d ff s 4f dim(4)d ff8 s 8f dim(4)d fcv s 10 varying dim(4)

d mb1 m style(*info) button(*OK)d rc s 9 0

Figura 105. Ejemplo VJNIRA.VPG (Pieza 1 de 2)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 333

Page 352: c 0924494

C *INZSR BEGSR

C eval fc = subrcac fc(2) dsply mb1 rcC eval fs = subrsac fs(2) dsply mb1 rc

C eval fp = subrpac fp(2) dsply mb1 rc

C eval fb = subrbac fb(2) dsply mb1 rc

C eval fi2= subri2ac fi2(2) dsply mb1 rc

C eval fi4= subri4ac fi4(2) dsply mb1 rc

C eval fu = subruac fu(2) dsply mb1 rc

C eval fd = subrdac fd(2) dsply mb1 rc

C eval ff = subrfa

c ff(2) dsply mb1 rc

C eval ff8= subrf8ac ff8(2) dsply mb1 rc

C eval fcv= subrcvac fcv(2) dsply mb1 rcC eval rc = %len(fcv(2))c rc dsply mb1 rcc seton lrC ENDSR

Figura 105. Ejemplo VJNIRA.VPG (Pieza 2 de 2)

334 Programación con VisualAge RPG

Page 353: c 0924494

// Archivo fuente: VSUBRA.C

// Función nativa que devuelve valores de matriz

// Añadir (d:\jdk12\include;d:\jdk12\include\win32) al valor INCLUDE para// poder encontrar jni.h al compilar.

// Compilado con: IBM VisualAge(TM) para C++ para Windows(R), Versión 3.5// Mandato de compilación: icc /q /ss /ge- /fe vsubra.dll vsubra.c

#include <stdio.h>#include <string.h>

#include <jni.h>

static void SwapBin2( char *);

static void SwapBin4( char *);

//---------------------------------------------------------------

jobjectArray _Export __stdcall Java_VJNIRA_SUBRCA( JNIEnv *je , void *jc){jobjectArray oa;jclass cls;jbyteArray ba;char *p;int i;

printf(" llamada a SUBRCA satisfactoria.\n");

// Crear el objeto matriz

cls = (*je)->FindClass( je, "java/lang/Object");if ( cls == NULL){

printf(" ERROR 1: FindClass.\n");return NULL;

}

Figura 106. Ejemplo VSUBRA.C (Pieza 1 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 335

Page 354: c 0924494

oa = (*je)->NewObjectArray( je, 4 /* longitud matriz */, cls, NULL );

if ( oa == NULL){

printf(" ERROR 2: Newobj\n");return NULL;

}

// Poblar la matrizfor (i=0; i<4; i++){// Crear un nuevo objeto de matriz de bytes para poder devolverlo.

ba = (*je)->NewByteArray( je, 10 /* = longitud matriz bytes */ );

// Establecer el valor del segundo elemento

if ( 1 == i){// Pinchar la memoria del elemento de la matriz de bytes para que

// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "Satisfactorio ",10);

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

}

(*je)->SetObjectArrayElement( je, oa, i /* elemento matriz, empieza en 0 */, ba);

} // for i

return oa;}//---------------------------------------------------------------

Figura 106. Ejemplo VSUBRA.C (Pieza 2 de 22)

336 Programación con VisualAge RPG

Page 355: c 0924494

jobjectArray _Export __stdcall Java_VJNIRA_SUBRSA( JNIEnv *je , void *jc){jobjectArray oa;int i;jclass cls;jmethodID mid;jobject rzo;

jbyteArray ba;char *p;

printf(" llamada a SUBRSA satisfactoria.\n");

// Crear el objeto matriz

cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgZoned");if ( cls == NULL){

printf(" ERROR 1: FindClass.\n");return NULL;

}

oa = (*je)->NewObjectArray( je, 4 /* longitud matriz */, cls, NULL );

if ( oa == NULL){

printf(" ERROR 2: Newobj\n");return NULL;

}

// Poblar la matrizfor (i=0; i<4; i++)

{

// Crear un nuevo objeto RpgZoned.

cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgZoned");if ( cls == NULL){

printf(" ERROR 1: FindClass.\n");return NULL;

}

Figura 106. Ejemplo VSUBRA.C (Pieza 3 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 337

Page 356: c 0924494

mid = (*je)->GetMethodID( je, cls, "<init>", "(II)V");

if ( mid == NULL){

printf(" ERROR: GetMethod.\n");return NULL;

}

rzo = (*je)->NewObject( je, cls, mid,(int) 5, /* núm. de dígitos */

(int) 0 /* núm. de posiciones decimales */);

if ( rzo == NULL){

printf(" ERROR3: \n");return NULL;

}

// Establecer el valor del segundo elementoif ( 1 == i){

// Para establecer el valor del objeto decimal con zona, necesitamos// una matriz de bytes Java para utilizarla como parámetro de entrada// del método para establecer el objeto decimal con zona.// Puede construirse un objeto de matriz de bytes nuevo u obtener uno

// recuperando el valor decimal con zona del objeto.

// Construir una matriz de bytes.

// Crear un objeto de matriz de bytes nuevo

ba = (*je)->NewByteArray( je, 5 /* = longitud matriz bytes */ );

if ( ba == NULL){

printf(" ERROR4: \n");return NULL;

}

Figura 106. Ejemplo VSUBRA.C (Pieza 4 de 22)

338 Programación con VisualAge RPG

Page 357: c 0924494

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "55555", 5);

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

// Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

// cls = (*je)->GetObjectClass(je, p1);// (clS) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

if ( mid == NULL){

printf(" ERROR 2: GetMethod.\n");return NULL;

}

(*je)->CallVoidMethod( je, rzo, mid,ba,(int) 1, // = Component.ZONED_TYPE0 // precisión

);

}

Figura 106. Ejemplo VSUBRA.C (Pieza 5 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 339

Page 358: c 0924494

(*je)->SetObjectArrayElement( je, oa, i /* elemento matriz, empieza en 0 */, rzo);

} // for i

return oa;

}//---------------------------------------------------------------

jobjectArray _Export __stdcall Java_VJNIRA_SUBRPA( JNIEnv *je , void *jc){jobjectArray oa;int i;jclass cls;jmethodID mid;jobject ro;

jbyteArray ba;char *p;

printf(" llamada a SUBRPA satisfactoria.\n");

// Crear el objeto matriz

cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgPacked");if ( cls == NULL){

printf(" ERROR 1: FindClass.\n");return NULL;

}

oa = (*je)->NewObjectArray( je, 4 /* longitud matriz */, cls, NULL );

if ( oa == NULL){

printf(" ERROR 2: Newobj\n");return NULL;

}

// Poblar la matrizfor (i=0; i<4; i++){

Figura 106. Ejemplo VSUBRA.C (Pieza 6 de 22)

340 Programación con VisualAge RPG

Page 359: c 0924494

// Crear un nuevo objeto RpgPacked.#if 0cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgPacked");if ( cls == NULL){

printf(" ERROR 1: FindClass.\n");return NULL;

}#endif

mid = (*je)->GetMethodID( je, cls, "<init>", "(II)V");

if ( mid == NULL){

printf(" ERROR: GetMethod.\n");return NULL;

}

ro = (*je)->NewObject( je, cls, mid,

(int) 5, /* núm. de dígitos */(int) 0 /* núm. de posiciones decimales */

);

if ( ro == NULL){

printf(" ERROR3: \n");return NULL;

}

// Establecer el valor del segundo elementoif ( 1 == i){

// Para establecer el valor del objeto decimal empaquetado, necesitamos// una matriz de bytes Java para utilizarla como parámetro de entrada// del método para establecer el objeto decimal empaquetado.// Puede construirse un objeto de matriz de bytes nuevo u obtener uno

// recuperando el valor decimal empaquetado del objeto.

// Construir una matriz de bytes.

Figura 106. Ejemplo VSUBRA.C (Pieza 7 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 341

Page 360: c 0924494

// Crear un objeto de matriz de bytes nuevo

ba = (*je)->NewByteArray( je, 3 /* = longitud matriz bytes */ );

if ( ba == NULL){

printf(" ERROR4: \n");return NULL;

}

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "\x55\x55\x5C", 3);

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

// Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

// cls = (*je)->GetObjectClass(je, p1);// (clS) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

if ( mid == NULL){

printf(" ERROR 2: GetMethod.\n");return NULL;

}

Figura 106. Ejemplo VSUBRA.C (Pieza 8 de 22)

342 Programación con VisualAge RPG

Page 361: c 0924494

(*je)->CallVoidMethod( je, ro, mid,ba, // El objeto de matriz de bytes(int) 2, // = Component.PACKED_TYPE

0 // posiciones decimales);

}

(*je)->SetObjectArrayElement( je, oa, i /* elemento matriz, empieza en 0 */, ro);

} // for i

return oa;}//---------------------------------------------------------------

jobjectArray _Export __stdcall Java_VJNIRA_SUBRBA( JNIEnv *je , void *jc){jobjectArray oa;int i;jclass cls;

jmethodID mid;jobject ro;

jbyteArray ba;char *p;

printf(" llamada a SUBRBA satisfactoria.\n");

// Crear el objeto matriz

cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgBinary");if ( cls == NULL){

printf(" ERROR 1: FindClass.\n");return NULL;

}

Figura 106. Ejemplo VSUBRA.C (Pieza 9 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 343

Page 362: c 0924494

oa = (*je)->NewObjectArray( je, 4 /* longitud matriz */, cls, NULL );

if ( oa == NULL){

printf(" ERROR 2: Newobj\n");

return NULL;}

// Poblar la matrizfor (i=0; i<4; i++){

// Crear un nuevo objeto RpgPacked.#if 0cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgBinary");if ( cls == NULL){

printf(" ERROR 1: FindClass.\n");return NULL;

}#endif

mid = (*je)->GetMethodID( je, cls, "<init>", "(II)V");

if ( mid == NULL){

printf(" ERROR: GetMethod.\n");return NULL;

}

ro = (*je)->NewObject( je, cls, mid,(int) 5, /* núm. de dígitos */(int) 0 /* núm. de posiciones decimales */

);

Figura 106. Ejemplo VSUBRA.C (Pieza 10 de 22)

344 Programación con VisualAge RPG

Page 363: c 0924494

if ( ro == NULL){

printf(" ERROR3: \n");return NULL;

}

// Establecer el valor del segundo elementoif ( 1 == i){

// Para establecer el valor del objeto decimal empaquetado, necesitamos// una matriz de bytes Java para utilizarla como parámetro de entrada// del método para establecer el objeto decimal empaquetado.

// Puede construirse un objeto de matriz de bytes nuevo u obtener uno// recuperando el valor decimal empaquetado del objeto.

// Construir una matriz de bytes.

// Crear un objeto de matriz de bytes nuevo

ba = (*je)->NewByteArray( je, 4 /* = longitud matriz bytes */ );

if ( ba == NULL){

printf(" ERROR4: \n");return NULL;

}

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "\x00\x00\xD9\x03", 4); // 55555 = 0xD903

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

Figura 106. Ejemplo VSUBRA.C (Pieza 11 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 345

Page 364: c 0924494

// Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al

// objeto RpgNumeric. Obtener el ID de método.

// cls = (*je)->GetObjectClass(je, p1);// (clS) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

if ( mid == NULL){

printf(" ERROR 2: GetMethod.\n");return NULL;

}

(*je)->CallVoidMethod( je, ro, mid,ba, // El objeto de matriz de bytes(int) 3, // = Component.Binary_TYPE

0 // posiciones decimales);

}

(*je)->SetObjectArrayElement( je, oa, i /* elemento matriz, empieza en 0 */, ro);

} // for i

return oa;}

Figura 106. Ejemplo VSUBRA.C (Pieza 12 de 22)

346 Programación con VisualAge RPG

Page 365: c 0924494

//---------------------------------------------------------------

jshortArray _Export __stdcall Java_VJNIRA_SUBRI2A( JNIEnv *je , void *jc){jshortArray rc;jshort *n;

printf(" llamada a SUBRI2A satisfactoria.\n");

rc = (*je)->NewShortArray( je, 4 /* = longitud matriz */ );

// Pinchar la memoria del elemento de la matriz para que// el lado nativo pueda acceder a ella.

n = (*je)->GetShortArrayElements( je, rc, NULL);

n[1] = -5555;

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseShortArrayElements( je, rc, n, 0);

return rc;}//---------------------------------------------------------------

jintArray _Export __stdcall Java_VJNIRA_SUBRI4A( JNIEnv *je , void *jc){jintArray rc;jint *n;printf(" llamada a SUBRI4A satisfactoria.\n");

rc = (*je)->NewIntArray( je, 4 /* = longitud matriz */ );

// Pinchar la memoria del elemento de la matriz para que// el lado nativo pueda acceder a ella.

n = (*je)->GetIntArrayElements( je, rc, NULL);

n[1] = -5555;

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseIntArrayElements( je, rc, n, 0);

return rc;}

Figura 106. Ejemplo VSUBRA.C (Pieza 13 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 347

Page 366: c 0924494

//---------------------------------------------------------------

jobjectArray _Export __stdcall Java_VJNIRA_SUBRUA( JNIEnv *je , void *jc){jobjectArray oa;int i;jclass cls;jmethodID mid;jobject ro;

jbyteArray ba;char *p;

printf(" llamada a SUBRUA satisfactoria.\n");

// Crear el objeto matriz

cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgUnsigned");

if ( cls == NULL){

printf(" ERROR 1: FindClass.\n");return NULL;

}

oa = (*je)->NewObjectArray( je, 4 /* longitud matriz */, cls, NULL );

if ( oa == NULL){

printf(" ERROR 2: Newobj\n");return NULL;

}

// Poblar la matrizfor (i=0; i<4; i++){

// Crear un nuevo objeto RpgPacked.#if 0cls = (*je)->FindClass( je, "com/ibm/varpg/rpgruntime/RpgUnsigned");if ( cls == NULL)

{printf(" ERROR 1: FindClass.\n");return NULL;

}#endif

Figura 106. Ejemplo VSUBRA.C (Pieza 14 de 22)

348 Programación con VisualAge RPG

Page 367: c 0924494

mid = (*je)->GetMethodID( je, cls, "<init>", "(II)V");

if ( mid == NULL){

printf(" ERROR: GetMethod.\n");return NULL;

}

ro = (*je)->NewObject( je, cls, mid,(int) 5, /* núm. de dígitos */(int) 0 /* núm. de posiciones decimales */

);

if ( ro == NULL)

{printf(" ERROR3: \n");return NULL;

}

// Establecer el valor del segundo elementoif ( 1 == i){

// Para establecer el valor del objeto decimal empaquetado, necesitamos// una matriz de bytes Java para utilizarla como parámetro de entrada// del método para establecer el objeto decimal empaquetado.// Puede construirse un objeto de matriz de bytes nuevo u obtener uno// recuperando el valor decimal empaquetado del objeto.

// Construir una matriz de bytes.

Figura 106. Ejemplo VSUBRA.C (Pieza 15 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 349

Page 368: c 0924494

// Crear un objeto de matriz de bytes nuevo

ba = (*je)->NewByteArray( je, 4 /* = longitud matriz bytes */ );

if ( ba == NULL){

printf(" ERROR4: \n");return NULL;

}

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "\x00\x00\xD9\x03", 4); // 55555 = 0xD903

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,

// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

Figura 106. Ejemplo VSUBRA.C (Pieza 16 de 22)

350 Programación con VisualAge RPG

Page 369: c 0924494

// Preparar la llamada al método desde la clase RpgNumeric que// toma un objeto de matriz de bytes y asigna su valor al// objeto RpgNumeric. Obtener el ID de método.

// cls = (*je)->GetObjectClass(je, p1);// (clS) sigue identificando el segundo parámetro. Reutilizar el valor

mid = (*je)->GetMethodID( je, cls, "assignFromNative", "([BII)V");

if ( mid == NULL){

printf(" ERROR 2: GetMethod.\n");return NULL;

}

(*je)->CallVoidMethod( je, ro, mid,ba, // El objeto de matriz de bytes(int) 5, // = Component.UNSIGNED_TYPE0 // posiciones decimales

);

}

(*je)->SetObjectArrayElement( je, oa, i /* elemento matriz, empieza en 0 */

, ro);} // for i

return oa;}//---------------------------------------------------------------

Figura 106. Ejemplo VSUBRA.C (Pieza 17 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 351

Page 370: c 0924494

jobjectArray _Export __stdcall Java_VJNIRA_SUBRDA( JNIEnv *je , void *jc){jobjectArray oa;jclass cls;jbyteArray ba;char *p;int i;

printf(" llamada a SUBRD satisfactoria.\n");

// Crear el objeto matriz

cls = (*je)->FindClass( je, "java/lang/Object");

if ( cls == NULL){

printf(" ERROR 1: FindClass.\n");return NULL;

}

oa = (*je)->NewObjectArray( je, 4 /* longitud matriz */, cls, NULL );

if ( oa == NULL){

printf(" ERROR 2: Newobj\n");return NULL;

}

// Poblar la matrizfor (i=0; i<4; i++){// Crear un nuevo objeto de matriz de bytes para poder devolverlo.

ba = (*je)->NewByteArray( je, 10 /* = longitud matriz bytes */ );

Figura 106. Ejemplo VSUBRA.C (Pieza 18 de 22)

352 Programación con VisualAge RPG

Page 371: c 0924494

// Establecer todos los elementos en un valor de fecha válido.

// Pinchar la memoria del elemento de la matriz de bytes para que// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "2000-01-01",10);

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);

(*je)->SetObjectArrayElement( je, oa, i /* elemento matriz, empieza en 0 */, ba);

} // for i

return oa;}//---------------------------------------------------------------

jfloatArray _Export __stdcall Java_VJNIRA_SUBRFA( JNIEnv *je , void *jc){jfloatArray rc;jfloat *n;

printf(" llamada a SUBRF satisfactoria.\n");

rc = (*je)->NewFloatArray( je, 4 /* = longitud matriz */ );

// Pinchar la memoria del elemento de la matriz para que// el lado nativo pueda acceder a ella.

n = (*je)->GetFloatArrayElements( je, rc, NULL);

n[1] = -4444.4444;

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseFloatArrayElements( je, rc, n, 0);

return rc;}

Figura 106. Ejemplo VSUBRA.C (Pieza 19 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 353

Page 372: c 0924494

//---------------------------------------------------------------

jdoubleArray _Export __stdcall Java_VJNIRA_SUBRF8A( JNIEnv *je , void *jc)

{jdoubleArray rc;jdouble *n;

printf(" llamada a SUBRF8 satisfactoria.\n");

rc = (*je)->NewDoubleArray( je, 4 /* = longitud matriz */ );

// Pinchar la memoria del elemento de la matriz para que// el lado nativo pueda acceder a ella.

n = (*je)->GetDoubleArrayElements( je, rc, NULL);

n[1] = -7777777.55555;

// Actualizar los valores y devolverlos al llamador Java

(*je)->ReleaseDoubleArrayElements( je, rc, n, 0);

return rc;

}//---------------------------------------------------------------

jobjectArray _Export __stdcall Java_VJNIRA_SUBRCVA( JNIEnv *je , void *jc){// Similar al caso de caracteres de longitud fija, sólo que los elementos// individuales de la matriz pueden crearse como matrices de bytes de// distintas longitudes para reflejar la longitud actual de los valores// de longitud variable.

Figura 106. Ejemplo VSUBRA.C (Pieza 20 de 22)

354 Programación con VisualAge RPG

Page 373: c 0924494

jobjectArray oa;jclass cls;jbyteArray ba;char *p;int i;

printf(" llamada a SUBRCVA satisfactoria.\n");

// Crear el objeto matriz

cls = (*je)->FindClass( je, "java/lang/Object");if ( cls == NULL){

printf(" ERROR 1: FindClass.\n");return NULL;

}

oa = (*je)->NewObjectArray( je, 4 /* longitud matriz */, cls, NULL );

if ( oa == NULL){

printf(" ERROR 2: Newobj\n");return NULL;

}

Figura 106. Ejemplo VSUBRA.C (Pieza 21 de 22)

Capítulo 20. Llamada a funciones del sistema al compilar para Java 355

Page 374: c 0924494

// Poblar la matrizfor (i=0; i<4; i++)

{// Crear un nuevo objeto de matriz de bytes para poder devolverlo.

ba = (*je)->NewByteArray( je,/* = longitud matriz bytes */(1==i) ? 4 : 10 );

// Establecer el valor del segundo elementoif ( 1 == i){// Pinchar la memoria del elemento de la matriz de bytes para que

// el lado nativo pueda acceder a ella.

p = (char *) (*je)->GetByteArrayElements( je, ba, NULL);

memcpy( p, "abcd",4);

// Actualizar los valores y devolverlos al llamador Java

// Cuarto parám. = 0 también hace que se libere el alm. de la variable,// por lo que no puede accederse a ellas tras llamar a esta función.

(*je)->ReleaseByteArrayElements( je, ba, (signed char *) p, 0);}

(*je)->SetObjectArrayElement( je, oa, i /* elemento matriz, empieza en 0 */, ba);

} // for i

return oa;}

Figura 106. Ejemplo VSUBRA.C (Pieza 22 de 22)

356 Programación con VisualAge RPG

Page 375: c 0924494

Capítulo 21. Cómo crear programas no GUI en VisualAge RPG

Esta sección describe cómo crear aplicaciones VARPG autónomas y bibliotecas deenlace dinámico (DLL). Las aplicaciones VARPG autónomas no tienen interfaz deusuario, pero pueden acceder archivos locales y de AS/400, así como ejecutarprogramas AS/400. Los archivos DLL son módulos que no pueden ejecutarsedirectamente; contienen procedimientos que pueden ser llamados por otrasaplicaciones VARPG. Los archivos DLL también pueden acceder a archivos locales,así como a archivos de AS/400 y programas. Los archivos DLL vienen a ser delmismo tipo que los programas de servicios de AS/400.

Puede crear aplicaciones VARPG autónomas en el diseñador de GUI de VARPG, obien emitiendo mandatos en una línea de mandatos de MS-DOS. (Consulte el“Apéndice C. Creación y compilación de programas no GUI desde MS-DOS” en lapágina 433 si desea información sobre los mandatos.) En este apartado se describecómo puede utilizar el Diseñador GUI para crear programas no GUI.

Al crear aplicaciones o archivos DLL, tenga en cuenta las siguientes restricciones:v Deben estar constituidos exclusivamente de procedimientos.v *ENTRY no está permitido.v Las subrutinas especiales *INZSR y *TERMSR no están permitidas.v Todas las subrutinas deben ser locales a un procedimiento.v La palabra clave EXPORT no está permitida al crear aplicaciones autónomas.v Debido a que ni las aplicaciones autónomas ni los archivos DLL tienen interfaz,

las incorporaciones %GETATR y %SETATR, y los códigos de operación GUI noestán permitidos. Entre ellos:– CLSWIN, GETATR, SETATR, START, STOP, SHOWWIN, READS

El código de operación DSPLY puede utilizarse. Sin embargo, si el procedimientoque lo contiene es invocado desde un archivo DLL de VisualAge RPG, el códigode operación DSPLY no hará nada. Asimismo, el código de operación DSPLY nosoporta un tipo de datos de mensaje en factor 1.

Cómo crear programas VARPG autónomosUn programa VARPG autónomo se crea cuando la palabra clave EXE se encuentraen la especificación de control.H EXE

El fuente del programa debe contener un procedimiento cuyo nombre coincida conel nombre del archivo fuente. Este será el principal punto de entrada del programa.Si deben pasarse parámetros al programa, deben especificarse en la definición deparámetros para el procedimiento principal y deben pasarse por valor. Es decir, lapalabra clave VALUE debe especificarse para cada parámetro. Al ejecutar unaaplicación desde la línea de mandatos debe separar los parámetros medianteespacios. Si se pasan más o menos parámetros de los especificados, no apareceráningún mensaje de error.

Para crear un programa autónomo en el Diseñador GUI, seleccione Proyecto >Nuevo > Proyecto no GUI De la ventana de proyectos. El editor abre un nuevoarchivo fuente que contiene una especificación de control H. Elimine el comentariopara la especificación H * EXE y escriba el código de su programa. Cuando haya

© Copyright IBM Corp. 1994, 2000 357

Page 376: c 0924494

terminado, guarde su proyecto y construya la aplicación. Asimismo, puedeseleccionar las opciones que desee desde la ventana de proyectos.

En el ejemplo siguiente, el programa autónomo VARPG acepta un únicoparámetro. Al ejecutarse, el programa convertirá el parámetro a mayúsculas ymostrará el resultado utilizando el código de operación DSPLY. Observe que elnombre del procedimiento principal, y el único, es MyPgm. Si desea intentar esteejemplo, asegúrese de dar al archivo el nombre MYPGM al guardarlo.* Programa de ejemplo autónomo VARPG

H EXE** Prototipo para el procedimiento principal

D MyPgm PRD 64A Value** Definición del procedimiento para MYPGM

PMyPgm B*

D MyPgm PID InString 64A Value*

D OutString S 64A*

D LC C 'abcdefghijklmnopqrstuvwxyz'D UC C 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'** Conversión del parámetro de entrada a mayúsculas y visualización

C lc:uc Xlate InString OutStringC OutString Dsply I 1*

PMyPgm E

Cómo crear archivos DLLUn archivo DLL se crea cuando la palabra clave NOMAIN se encuentra en laespecificación de control:H NOMAIN

Para crear un archivo DLL en el Diseñador GUI, seleccione Proyecto > Nuevo >Proyecto no GUI de la ventana de proyectos. El editor abre un nuevo archivofuente que contiene una especificación de control H. Elimine el comentario para laespecificación H * NOMAIN y escriba el código de su programa. Cuando hayaterminado, guarde su proyecto y construya el archivo DLL. Asimismo, puedeseleccionar las opciones que desee desde la ventana de proyectos.

Al construir un archivo DLL, el compilador produce el archivo DLL y un archivoLIB. El archivo LIB se utiliza para enlazar el archivo DLL a otras aplicaciones. Elarchivo LIB debe encontrarse en el mismo directorio que el fuente y debe tener elmismo nombre que el archivo DLL. El archivo LIB contiene todos losprocedimientos que tienen la palabra clave EXPORT en su especificación P Begin.

El siguiente ejemplo le muestra cómo codificar la parte del programa MyPGM queconvierte la serie de minúsculas a mayúsculas como un procedimiento en unarchivo DLL. El fuente para el archivo DLL contiene un procedimiento llamadoToUpper. Agregue la palabra clave Export a la definición del procedimiento paraque éste pueda invocarse desde otros programas.

* Ejemplo de archivo DLL VARPGH NOMAIN*

358 Programación con VisualAge RPG

Page 377: c 0924494

* Procedimiento prototipo ToUpperD ToUpper PR 64AD 64A Value** El procedimiento ToUpper

PToUpper B Export*

D ToUpper PI 64AD InString 64A Value*

D OutString S 64A*

D LC C 'abcdefghijklmnopqrstuvwxyz'D UC C 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'**

C lc:uc Xlate InString OutStringC Return OutString*

PToUpper E

Al crear y construir un archivo DLL, puede nombrarlo como guste. Para esteejemplo, hemos utilizado el nombre MyFunc. Una construcción satisfactoria crearálos siguientes archivos en el directorio fuente:v MyFunc.VPG - fuente del programav MyFunc.DLL - el archivo DLLv MyFunc.LST - el listado del compiladorv MyFunc.LIB - el archivo de bibliotecav MyFunc.EVT - el archivo de sucesos (utilizado por el Diseñador GUI para

visualizar la ventana de errores, aunque no es necesario para ejecutar elprograma)

Abra y modifique el fuente MyPGM para que llame al procedimiento ToUpper enel archivo MyFunc.DLL que acaba de crearse. El fuente modificado será:

0000 * Llamada a un procedimiento en un archivo DLL VARPG0001 H EXE0002 *

0003 D ToUpper PR 64A DLL('MyFunc')0004 D ExtProc('TOUPPER')0006 D 64A Value

0007 *0008 D MyMain PR0009 D 64A Value0010 *0011 PMyMain B0012 *0013 D MyMain PI0014 D InString 64A Value0015 *0016 D Upper S 64A0017 *

0018 C Eval Upper=ToUpper(Instring)

0019 C Upper Dsply I 10010 *0011 PMyMain E

lín. Descripción de cambio

0003 Defina el prototipo para el procedimiento ToUpper y especifique que el

Capítulo 21. Cómo crear programas no GUI en VisualAge RPG 359

Page 378: c 0924494

procedimiento devuelva un parámetro que sea un campo alpha de 64 bytesde longitud. La palabra clave del archivo DLL especifica que elprocedimiento se encuentra en el archivo DLL llamado MyFunc.DLL.

0004 La palabra clave ExtProc especifica el nombre del procedimiento que debeinvocarse. El nombre es el mismo que el que hemos empleado en laespecificación Definition (línea 0003), por lo que puede omitir la palabraclave. Si decide, de todas formas, especificar el nombre, éste deberáaparecer en mayúsculas, como se indica.

0006 Esta sentencia indica que el procedimiento espera un parámetro - uncampo alpha de 64 caracteres de longitud. En este caso, es VALUE quienpasa el parámetro.

0018 Esta es la llamada al procedimiento.

Si el procedimiento que está invocando no le devuelve un valor, debe utilizar elcódigo de operación CALLP para invocarlo:

C CALLP SomeFunc(parm1:parm2)

360 Programación con VisualAge RPG

Page 379: c 0924494

ExcepcionesEl tratamiento de las excepciones difiere del de las aplicaciones GUI VARPG porvarias razones:v No se devuelve ninguna información sobre la excepción al emisor si éste no

reside en la DLL de utilidad.v El manejador de excepciones por omisión no se invoca nunca desde un archivo

DLL ya que no se invoca cuando se produce una excepción en unprocedimiento. Si se produce una excepción en el archivo DLL y no hay ningúnindicador de errores ni *PSSR, el archivo DLL finaliza. La información sobre laexcepción se escribe en el archivo FVDCERRS.LOG.

v La manera más adecuada de tratar excepciones en un archivo DLL de utilidad estener un indicador de errores, o un *PSSR local para cada rutina que devuelvaun código de devolución apropiado al emisor.

Cómo depurar aplicacionesPara depurar programas VARPG, asegúrese de utilizar la opción de compilador dedepuración cuando construya la aplicación. Si no ha establecido la opción dedepuración, aún puede iniciar el depurador en el programa, pero deberá trabajarcon la vista de ensamblador de su programa.

Para ejecutar el depurador contra su fuente, debe antes construir su aplicación. Enla ventana de proyectos, seleccione Proyecto > Construir > Windows NT/95/98.Para arrancar el depurador, seleccione el elemento de menú Depurar del menúProyecto. Consulte el “Capítulo 10. Depuración de la aplicación” en la página 217 sidesea más información sobre depuración.

Procedimientos de depuraciónSi desea depurar código en su archivo DLL, debe seguir algunos pasos más:1. Inicie el depurador para su aplicación principal; en nuestro ejemplo, MyMain.2. En el diálogo Depurador - Control de sesión, seleccione Puntos de

interrupción-Establecer aparición de carga....3. Cuando aparezca el diálogo Punto de interrupción de aparición de carga,

escriba el nombre del archivo DLL, MyFunc, en la entrada Nombre del archivoDLL y pulse Aceptar.

4. Ejecute su programa.

Cuando se invoca el proceso en el archivo DLL, se visualiza un diálogo de mensajedel depurador que indica que se está cargando el archivo DLL. Pulse Aceptar yhaga lo siguiente:1. Localice el diálogo Depurador - Control de sesión y observe que hay una nueva

entrada en el panel de la derecha con el nombre del archivo DLL.

Capítulo 21. Cómo crear programas no GUI en VisualAge RPG 361

Page 380: c 0924494

2. Pulse el botón con el signo + junto al nombre del archivo DLL. Se expandirápara mostrar el nombre del módulo de objeto, MyFunc.obj.

3. Efectúe una doble pulsación en el nombre del módulo de objeto.4. La vista del fuente del depurador mostrará ahora el fuente para el

procedimiento ToUpper en el archivo DLL MYFUNC.

Ahora puede añadir puntos de interrupción y visualizar variables de programa enel archivo DLL. Asimismo, si está iniciando (START) otros componentes VARPG, obien, si está invocando sus propias funciones ’C’, también puede utilizar losprocedimientos descritos más arriba para depurarlos.

Figura 107. Selección del archivo de objeto MyFunc.DLL

362 Programación con VisualAge RPG

Page 381: c 0924494

Capítulo 22. Consideraciones sobre DBCS

Si piensa utilizar VisualAge RPG en un sistema de Juego de Caracteres de DobleByte (DBCS), debe tener en cuenta lo siguiente:v El compilador no permite caracteres de desplazamiento a teclado ideográfico y a

teclado estándar en los literales. Si utiliza el editor de VisualAge RPG para abrirun miembro AS/400 con el fin de copiar el fuente en el programa VisualAgeRPG, debe eliminar los caracteres de desplazamiento a teclado ideográfico y ateclado estándar de todos los literales. Si no se eliminan, se producirán erroresen la compilación.

v El compilador elimina los caracteres de desplazamiento a teclado ideográfico y ateclado estándar de los miembros fuente VisualAge RPG cuando se recuperanmediante la característica /COPY remota.

v Los caracteres DBCS no están permitidos en la extensión de los nombres dearchivo de los iconos de una aplicación.

v Un nombre de aplicación VisualAge RPG que contenga caracteres que no seanDBCS provoca una anomalía en la compilación.

Soporte de VisualAge RPG para tipos de datos DBCSVisualAge RPG soporta varios tipos de datos DBCS. Cuando se ejecuta laaplicación, se siguen ciertas normas al utilizar tipos de datos DBCS con el fin deasegurar que los datos se transfieren correctamente entre el servidor AS/400 y laestación de trabajo. Están soportados los siguientes tipos de datos DBCS:

Sólo DBCSUn campo de este tipo de datos sólo contiene datos DBCS y debe utilizarseal usar la base de datos de AS/400. Equivale al tipo de datos J soportadopor la base de datos de AS/400.

DBCS cualquieraUn campo de este tipo de datos puede contener datos de byte único ydatos DBCS a la vez. Debe utilizarse al usar la base de datos de AS/400.Equivale al tipo de datos E soportado por la base de datos de AS/400.

DBCS mixtoUn campo de este tipo de datos puede contener datos de byte único ydatos DBCS a la vez. Debe utilizarse al intercambiar datos con la base dedatos de AS/400. Equivale al tipo de datos O soportado por la base dedatos de AS/400.

Los tipos de datos de AS/400 J, O y E requieren que los datos DBCS esténencerrados entre caracteres SO (Desplazamiento a teclado ideográfico) y SI(Desplazamiento a teclado estándar). Los campos de estación de trabajo DBCScualquiera, DBCS mixto y Sólo DBCS no utilizan caracteres SO y SI. Cuando seutilizan estos campos para transferir datos al servidor, los caracteres SO y SI seañaden según sea apropiado. Al recuperar datos del servidor, se eliminan loscaracteres SO y SI y el campo VisualAge RPG se rellena con dos blancos de byteúnico.

DBCS cualquiera, DBCS mixto y Sólo DBCS se representan como campos de tipocarácter con el mismo nombre que sus nombres de componente en la aplicaciónVisualAge RPG.

© Copyright IBM Corp. 1994, 2000 363

Page 382: c 0924494

El siguiente ejemplo muestra cómo se convierten los datos cuando se transfierendatos DBCS a y desde el servidor. En este ejemplo, se crea un campo Sólo DBCSde 10 bytes utilizando VisualAge RPG. Esto quiere decir que el campo puedecontener cuatro caracteres DBCS ya que cada carácter DBCS requiere dos bytes.Los dos bytes extra se utilizan para insertar los caracteres SO y SI antes detransferir el campo al servidor. Suponga que el campo contiene los siguientes datosantes de transferirse al servidor:

DBDBDBDBblbl

donde DB = 1 Carácter de doble byte.bl = 1 Carácter blanco de byte único.

Antes de transferir el campo al servidor, se convierte de tal manera que los datosDBCS quedan encerrados entre los caracteres SO y SI. Los blancos de byte único seconsideran insignificantes y se sustituyen por los caracteres SO y SI adecuados. Porconsiguiente, el campo aparecerá de la manera siguiente antes de transferirse alservidor:

SODBDBDBDBSI

Si se recuperan los mismos datos del servidor, se eliminan los caracteres SO y SI yel campo se rellena con dos blancos de byte único:

DBDBDBDBblbl

donde DB = 1 Carácter de doble bytebl = 1 Carácter blanco de byte único

Nota: Los campos de tipo carácter que representan los tipos de datos Sólo DBCS,DBCS mixto o DBCS cualquiera deben rellenarse con el número adecuadode blancos de byte único con el fin de que el campo se transfiera al servidory los datos del campo se visualicen correctamente en la ventana.

VisualAge RPG asegura que haya suficientes blancos de byte único. Al establecercampos DBCS o recuperar información de campos DBCS mediante los códigos deoperación SETATR y GETATR respectivamente, debe asegurarse de que la longituddel campo en las operaciones SETATR y GETATR sea igual que la del campo en laventana. Si el campo no tiene la misma longitud, no podrá transferirse entre elservidor y la estación de trabajo.

Tipo de datos Sólo DBCSVisualAge RPG asegura lo siguiente cuando se utiliza el tipo de datos Sólo DBCS,independientemente de si los datos se añaden a través del campo en la ventana osi se entran mediante el código de operación SETATR:v La longitud mínima del campo es de 2. Esto asegura que haya espacio suficiente

para los caracteres SO y SI que se añaden cuando se transfieren los datos alservidor.

v El campo contiene caracteres DBCS válidos. Cada par de doble byte secomprueba para asegurar que se utiliza un carácter DBCS válido.

v El campo se rellena con blancos de la manera adecuada. Si se entra un valormenor de lo que permite el campo, éste se rellena hasta la longitud máxima de 2con blancos de doble byte. Los dos últimos bytes del campo se rellenan conblancos de byte único.

364 Programación con VisualAge RPG

Page 383: c 0924494

Tipo de datos DBCS cualquieraEl tipo de datos DBCS cualquiera sólo puede contener todos los datos de byteúnico o todos los datos de doble byte: no está permitida la mezcla de datos DBCSy de byte único. Si se utilizan datos de byte único, puede utilizarse la longitudmáxima del campo para contener los datos de byte único y puede transferirse lalongitud máxima de datos a y desde el servidor.

VisualAge RPG impone las siguientes reglas cuando los dos primeros bytes delcampo representan un carácter DBCS, independientemente de si los datos seañaden a través del campo en la ventana o si se entran mediante el código deoperación SETATR:v La longitud mínima del campo es de 2. Esto asegura que haya espacio suficiente

para los caracteres SO y SI que se añaden cuando se transfieren los datos alservidor.

v El campo sólo contiene caracteres DBCS válidos. Cada par de doble byte secomprueba para asegurar que se utiliza un carácter DBCS válido.

v El campo se rellena con blancos de la manera adecuada. Si se entra un valormenor de lo que permite el campo, éste se rellena hasta la longitud máxima de 2con blancos de doble byte. Los dos últimos bytes del campo se rellenan conblancos de byte único.

Tipo de datos DBCS mixtoEste campo puede contener cualquier número de caracteres DBCS o de byte únicode manera intercambiable. VisualAge RPG impone las siguientes reglas:v Este campo de tipo carácter siempre se rellena con blancos de byte único.v Por cada cambio en la modalidad DBCS, debe contabilizarse un carácter SO y SI.

Cada vez que el usuario pasa a entrar caracteres DBCS o de byte único, se restandos de la longitud máxima que puede entrarse. Por ejemplo, suponga que secrea un campo de DBCS mixto con una longitud igual a 20 utilizando VisualAgeRPG. Este campo tiene el siguiente valor:

DBsbDBsbDBsbDBsb.

donde DB = 1 carácter DBCS.sb = 1 carácter de byte único.

Es la máxima longitud del campo, ya que éste se convierte a lo siguiente antesde transferirse al servidor.

SODBSIsbSODBSIsbSODBSIsbSODBSIsb.

donde SO = 1 carácter de desplazamiento a teclado ideográfico.sb = 1 carácter de desplazamiento a teclado estándar.

Se utilizan los 20 bytes del campo.

Consideraciones sobre DBCS puroTanto el lenguaje VisualAge RPG como el soporte de base de datos de AS/400soportan un tipo de datos DBCS puro: el tipo de datos G o Gráfico. Los datos deDBCS puro no requieren caracteres SO (Desplazamiento a teclado ideográfico) o SI(Desplazamiento a teclado estándar) en el servidor AS/400 ni en la estación detrabajo. Cuando se convierten datos gráficos entre el servidor AS/400 y la estaciónde trabajo, no se añade ni se elimina ningún carácter SO o SI.

Los campos de entrada GUI no se correlacionan directamente con el tipo de datosgráficos soportado en el lenguaje VisualAge RPG. Para utilizar el campo en toda su

Capítulo 22. Consideraciones sobre DBCS 365

Page 384: c 0924494

amplitud, se recomienda que cree una entrada de caracteres en la ventana. Alhacerlo, se crea un campo de tipo carácter VisualAge RPG con el mismo nombreque el componente Diseñador GUI. Entonces puede utilizarse un campo Gráficodistinto para interactuar con el campo de entrada de caracteres creado mediante elDiseñador GUI. Utilice el código de operación SETATR o GETATR para interactuarcon los campos de entrada. De esta manera, puede utilizarse toda la longitud delcampo de entrada para almacenar caracteres DBCS sin preocuparse por loscaracteres SO y SI.

366 Programación con VisualAge RPG

Page 385: c 0924494

Capítulo 23. Fusión de código en la aplicación

Durante el proceso de programación es posible que desee fusionar dos o máscomponentes de un proyecto o componente lógico con el código asociado. Puedeutilizar la función Fusionar para llevarlo a cabo. Seleccione el elemento de menúFusionar en el menú desplegable Proyecto. Aparecerá el recuadro de diálogo AbrirComponente - VisualAge RPG que le permitirá seleccionar el proyecto del quedesea realizar el proceso de fusión.

El aspecto y la función de este recuadro de diálogo es similar al recuadro dediálogo Buscar carpeta/proyecto. Se puede especificar el proyecto en el campo deentrada, incluyendo la vía de acceso completa, o puede utilizarse el recuadro delista para seleccionar una unidad y las carpetas para buscar el proyecto necesario.Estos dos métodos abrirán la ventana Vista de árbol de objetos GUI del proyectoespecificado. Asimismo, se puede seleccionar el elemento de menú Objetos GUI enel menú desplegable Ver del organizador de proyectos.

En esta ventana se muestran dos vistas; la de la izquierda contiene la vista de árboldel proyecto del que desea realizar el proceso de fusión, y la de la derechacontiene todos los hijos del componente seleccionado en la vista de árbol de laizquierda. Se pueden seleccionar varios componentes en la parte derecha de laventana, de forma similar al Explorador de Windows. Esta vista se puede utilizarcomo paleta de componentes adicionales porque en ella pueden seleccionarseelementos (en el panel izquierdo o derecho) y, a continuación, señalarlos ypulsarlos en la vista de árbol del proyecto en uso o en la ventana de diseño. Estofunciona de forma similar a la paleta de componentes en el sentido de que sólo sepueden colocar componentes en componentes basados en marcos y éstos, a su vez,sólo se pueden colocar en la raíz del árbol del proyecto. Al fusionar la GUI y el

Figura 108. La vista de árbol de objetos GUI para fusión de código

© Copyright IBM Corp. 1994, 2000 367

Page 386: c 0924494

código asociado, el constructor obligará a guardar el proyecto en uso para podercontar con una copia de seguridad del trabajo en caso de que los resultados de lafusión no le satisfagan.

Además del diseño de la GUI, la fusión copiará subrutinas de acción enlazadas,paneles de ayuda, descripciones técnicas, referencias a archivos de soporte,subrutinas de usuarios referenciadas y mensajes de usuario. Hay que tener encuenta varias reglas al fusionar código en estos casos específicos.v Se copiarán todas las subrutinas de acción enlazadas.v Los archivos de soporte referenciados no se copiarán con las referencias. Esto es

responsabilidad del programador.v Las especificaciones de las descripciones de archivos y las especificaciones de

definiciones no se copiarán en el proyecto en uso. Esto también esresponsabilidad del programador.

v Las subrutinas de usuario, los procedimientos RPG y los mensajes de usuarioreferenciados por la subrutina de acción que se copia también se copiarán. Estoincluye todas las referencias a subrutinas de usuario utilizadas por un código deoperación EXSR o CASxx, los procedimientos RPG referenciados en un códigode operación CALLP y los mensajes de usuario referenciados con el código deoperación DSPLY.

v En el caso de los componentes cuyo nombre ha sido modificado, también secambiará el nombre de todas las subrutinas de acción que hacen referencia alcomponente y que tienen nombres que se ajustan al formato estándar. Porejemplo, el nombre del siguiente código fuente se cambiaría, ya que sigue elformato estándar. El requisito de este formato es que el nombre del componentey de la ventana correspondan directamente con la ubicación donde puedeencontrarse el componente.*...1....+....2....+....3....+....4....+....5....+....6....+....7....+....8CSRN01Factor1+++++++Opcode(E)+Factor2+++++++Result++++++++Len++D+HiLoEq----C PSB000000C BEGACT PRESS FRA000000B

.

.

.C ENDACT

v Los nombres de los mensajes de usuario copiados se cambian consecutivamenteempezando por el primer mensaje copiado. Todos los mensajes de usuariofusionados se numeran secuencialmente empezando inmediatamente despuésdel último mensaje del proyecto en uso. Los ID de mensaje se modifican encódigos de operación DSPLY que hacen referencia a ellos.

v Si se detecta un conflicto de nombres para una subrutina de usuario, no semodificará el nombre y se añadirá a una lista contenida en el archivo de registrode fusión. El registro también se visualizará en la ventana Resultado de la fusiónde código. El archivo de registro de fusión se ubicará en el directorio delproyecto, con el nombre de nombre_proyecto.mrg, donde nombre_proyecto es elnombre del proyecto. Este archivo será sustituido si se realiza más de una fusiónpara el mismo proyecto. El archivo no se añade automáticamente. El siguienteejemplo comprende un listado de un archivo de fusión de ejemplo.

368 Programación con VisualAge RPG

Page 387: c 0924494

Los componentes siguientes se han copiado en el proyecto de destino:

Nombre de origen Nombre de destino

SEARCHW:CAN00023 SEARCHW:CAN00023SEARCHW:SEARCHW SEARCHW:SEARCHWSEARCHW:SEARCHGB SEARCHW:SEARCHGBSEARCHW:STX00071 SEARCHW:STX00071SEARCHW:TITLECB SEARCHW:TITLECBSEARCHW:STX00073 SEARCHW:STX00073SEARCHW:STX00074 SEARCHW:STX00074SEARCHW:STX00075 SEARCHW:STX00075SEARCHW:CATCB SEARCHW:CATCBSEARCHW:DIRCB SEARCHW:DIRCBSEARCHW:ACTORCB SEARCHW:ACTORCBSEARCHW:SEARCHPB SEARCHW:SEARCHPBSEARCHW:CANCELSEPB SEARCHW:CANCELSEPBSEARCHW:HELPPB SEARCHW:HELPPBSEARCHW:STX00082 SEARCHW:STX00082

Los paneles de ayuda siguientes se han copiado en el proyecto de destino:

Nombre de origen Nombre de destino

24.SEARCHW 88.SEARCHW79.SEARCHPB 99.SEARCHPB80.CANCELSEPB 100.CANCELSEPB81.HELPPB 101.HELPPB

Fusionando código fuente:

Subrutina de acción CATW+CLOSE+CATWRedenominando a SEARCHW+CLOSE+SEARCHW

Subrutina de acción TITLECB+CREATE+SEARCHWSubrutina de acción DIRCB+CREATE+SEARCHWSubrutina de acción ACTORCB+CREATE+SEARCHWSubrutina de acción CATCB+CREATE+SEARCHWSubrutina de acción TITLECB+ENTER+SEARCHWSubrutina de acción CATCB+SELECT+SEARCHWSubrutina de acción DIRCB+SELECT+SEARCHWSubrutina de acción ACTORCB+SELECT+SEARCHWSubrutina de acción CANCELSEPB+PRESS+SEARCHWSubrutina de acción SEARCHPB+PRESS+SEARCHWMensaje *MSG0001 -> *MSG0003Mensaje *MSG0001 -> *MSG0003Mensaje *MSG0001 -> *MSG0003Mensaje *MSG0001 -> *MSG0003

Subrutina de usuario WRTBRSFSRSubrutina de usuario CASECATSubrutina de usuario CKCRITERIASubrutina de usuario DSPBROWSEMensaje *MSG0001 -> *MSG0003

Subrutina de usuario BRACTIONSubrutina de usuario BRCHILDRENSubrutina de usuario BRSCIFISubrutina de usuario BRCOMEDYSubrutina de usuario BRHORRORSubrutina de usuario BRWESTERNSubrutina de usuario BRROMANCESubrutina de usuario BRCLASSIC

Capítulo 23. Fusión de código en la aplicación 369

Page 388: c 0924494

Las reglas siguientes se aplican a la resolución de conflictos de nombres decomponentes:v Se cambiará el nombre del componente o de la ventana fusionado.v Si se cambia el nombre de una ventana, todos los componentes contenidos en

ella recibirán el nombre de la nueva ventana.v Las subrutinas de acción enlazadas con una ventana o componente

redenominado serán redenominadas y reenlazadas, siempre que tengan elformato estándar de nombres.

v Se cambiarán las especificaciones de los cálculos que contengan un código deoperación GETATR o SETATR que haga referencia a un componenteredenominado.

v El proceso de fusión intenta corregir las referencias de componentes en el códigofusionado según los cambios de nombre de los componentes.

También se copian los mensajes de usuario utilizados en los componentesfusionados. Se aplican las reglas siguientes:v Si existe un conflicto de nombres en un mensaje de usuario, se producirá un

cambio de nombre.v Se actualizarán las referencias a mensajes de usuario redenominados.

Los mensajes siguientes se han copiado en el proyecto de destino:

Mensaje de origen Mensaje de destino

1 3

Las descripciones técnicas de los siguientes componentes se han copiado enel proyecto de destino:

Nombre de origen Nombre de destino

SEARCHW:SEARCHPB SEARCHW:SEARCHPBSEARCHW:CANCELSEPB SEARCHW:CANCELSEPBSEARCHW:HELPPB SEARCHW:HELPPB

370 Programación con VisualAge RPG

Page 389: c 0924494

Capítulo 24. Conectores de proveedor

Los conectores son aplicaciones escritas por desarrolladores de terceras empresas ycreadas para proporcionar mayor funcionalidad a VisualAge RPG. Se puedeautomatizar una gran variedad de tareas, como la inserción de una línea de códigopara definir el valor de un atributo seleccionado de una lista para un componentedeterminado; o un procedimiento que permita que los programadores impriman elfuente RPG formateado para incluir cabeceras y pies de página.

Adición de conectores de proveedorPara añadir un conector creado u obtenido de un desarrollador de otra empresa,siga los siguientes pasos:1. Pulse el botón sobre el menú desplegable Proveedor.2. Resalte el elemento Conectores para activar el submenú de conectores.3. Pulse el botón sobre el mandato Añadir conector... para abrir la ventana

Añadir conector.4. Seleccione el conector de proveedor que desea añadir de entre los archivos

visualizados en la ventana. Los archivos visualizados tienen la extensión .plg.

Invocación de un conector de proveedorUna vez se ha añadido un conector al Diseñador GUI de VisualAge RPG, hay queinvocar la función. La manera más sencilla de hacerlo consiste en seleccionar elelemento de menú correspondiente al conector que ha sido definido por elproveedor. Este elemento de menú puede encontrarse en el menú desplegableProveedor, Seleccionado o en el menú emergente de un componente. En algunoscasos el conector no tendrá ningún elemento de menú definido y será necesarioinvocarlo de forma externa al Diseñador GUI (para ver un ejemplo de este métodode invocación, consulte el conector de ejemplo LPEXSAMP). Como ejemplo, añadauno o varios de los conectores de proveedor de ejemplo proporcionados conVisualAge RPG. Para invocar estos conectores, siga los siguientes pasos:1. Pulse el botón sobre el menú desplegable Proveedor.2. Resalte el elemento Conectores para activar el submenú de conectores.3. Resalte el elemento de menú añadido junto con el conector. El nombre de este

elemento de menú es variable porque está creado por el desarrollador delconector. Puede aparecer otro submenú, dependiendo deldesarrollador/proveedor. En este caso, vaya al paso 4; de lo contrario, pulse elbotón sobre el elemento de menú para invocar el conector.

4. Pulse el botón sobre el elemento de menú adecuado del submenú para invocarel conector.

Gestión de conectores de proveedorSi dispone de conectores de proveedor en VisualAge RPG, es interesante conocer lainformación acerca del conector como, por ejemplo, el desarrollador, la descripcióndel desarrollador sobre el conector y para qué sirve o la dll asociada con el mismo.Esta información puede obtenerse en la ventana Gestionar conectores.

Para abrir la ventana Gestionar conectores, siga los siguientes pasos:1. Pulse el botón sobre el menú desplegable Proveedor.2. Resalte el elemento Conectores para activar el submenú de conectores.

© Copyright IBM Corp. 1994, 2000 371

Page 390: c 0924494

3. Pulse el botón sobre el mandato Gestionar conectores... para abrir la ventanaGestionar conectores.

372 Programación con VisualAge RPG

Page 391: c 0924494

Capítulo 25. Creación de conectores

Se puede crear un conector para satisfacer necesidades específicas o comosuplemento de VisualAge RPG para enviarlo a otros programadores a los quepueda serles útil. Los conectores pueden crearse utilizando VisualAge C++ o REXXde VisualAge RPG. A continuación se describe el proceso de creación de conectoresmediante código de VisualAge RPG. Seguirán secciones adicionales que tratan lasexcepciones y las normas básicas de creación de conectores con VisualAge C++ oREXX.

Creación de conectores mediante VisualAge RPGHay dos componentes necesarios para crear un conector: el archivo ejecutable y elarchivo de información del conector. El archivo ejecutable consta de código fuentecompilado que realiza la función deseada. El archivo de información del conector(.plg) actúa de interfaz entre el Diseñador GUI y el archivo ejecutable. Contieneinformación importante como las definiciones de los elementos del menúdesplegable que se añaden al Diseñador GUI y la llamada al archivo ejecutable.

El orden de creación de los archivos no es importante, ya que ambos deben estarpresentes para que el conector funcione. Este ejemplo empieza por el archivo .plg.

Creación del archivo .plgEl archivo .plg actúa de interfaz entre el conector y el diseñador. Es un archivoASCII que contiene información de organización, como la ubicación de la DLLnecesaria, la ubicación de los archivos de ayuda asociados y el nombre del propioconector y del proveedor. El archivo .plg también contiene la información necesariapara actuar de interfaz entre el conector y el diseñador. Se incluye la serie de lalínea de mandatos, el texto deseado para los elementos de menú y la combinaciónde teclas aceleradoras. En la siguiente lista de palabras clave se explican losdistintos parámetros, incluidas las reglas pertinentes, tanto si el parámetro esnecesario como opcional, y la información que hay que proporcionar. Acontinuación de la lista de palabras clave se muestra un ejemplo del archivocuando está finalizado.

Nota: Los espacios entre la palabra clave y el valor del parámetro utilizado para elvalor en el conector son arbitrarios. Los espacios utilizados en los ejemplosresponden únicamente a una cuestión de diseño.

Alternate_PathsEs una serie que indica las vías de acceso relativas que deben utilizarse al cargar laDLL del conector descrita más abajo. Este campo es opcional.

Esta serie adopta la forma:"&1\víaRelativa1;&1víaRelativa2;...;&1\víaRelativaN;"

donde &1\ se convertirá en la vía de acceso completa del archivo .plg. Esto implicaque si se dispone de un conjunto de conectores que se instalan en un directoriocomo c:\myplugins y todos ellos están enlazados con una DLL común:c:\myplugins\plugutil\plugutil.dll, en caso de que todos los conectores seencuentren en c:\myplugins\plugN\plugN.plg, se podría especificar la vía deacceso alternativa: &1\..\util;, que se convertiría en:

© Copyright IBM Corp. 1994, 2000 373

Page 392: c 0924494

c:\myplugins\plugN\..\util; y se añadiría a PATH antes de cargar la DLL. Lascomillas son necesarias si se decide utilizar esta palabra clave.

En lugar de una serie, también se puede utilizar un ID de recurso para apuntar auna vía de acceso especificada en un fuente externo.

DLL_NamesEl valor de este campo es una serie que define el nombre de los archivos DLLnecesarios para este conector. Es un campo opcional; si se utiliza, debe haber elnombre de una DLL utilizada por el conector. Además, puede darse el nombremri.dll. Este nombre es opcional, pero no puede incluirse sin la DLLcorrespondiente. Si se incluyen los dos, se delimitan con un espacio. El nombre delos archivos DLL puede comprender la vía de acceso relativa a la ubicación de losarchivos del conector.

conector.dllEs el nombre de la DLL que contiene el código del conector. Puedeomitirse si el conector no es una llamada de función dentro de una DLL.

mri.dllSi el MRI (series traducibles) se encuentran en una DLL diferente, indiquesu nombre. Primero se especifican las DLL para que las series que debanseguirse puedan incluirse en las DLL.

Cuando una serie es necesaria más adelante en el archivo .plg, si no se especificauna serie entre comillas, se presupone que el valor dado es un ID de recurso deserie en mri.dll o conector.dll

Vendor_NameEs el nombre del proveedor especificado entre comillas dobles o del ID de recursode una serie. Este campo es opcional, pero recomendado. Un ejemplo de esta seriesería:Vendor_Name: "Plug-Me-In Inc."

Plugin_NameEs el nombre del conector especificado entre comillas o del ID de recurso de unaserie. Este campo es opcional, pero recomendado. Un ejemplo de este campo conuna serie es:Plugin_Name: "Who Am I?"

Help_FileEste campo es opcional e identifica el archivo .hlp de Windows utilizado paravisualizar ayuda para los elementos de menú. Es una serie que no lleva comillas yque incluye la vía de acceso relativa del archivo de ayuda.

Unloading_FunctionEste campo es opcional. El campo Unloading_Function no puede utilizarse juntocon el campo Unloading_Command_Line. Este campo sólo se utiliza si hayinformación o un elemento de visualización que tiene que modificarse o eliminarsecuando se ha finalizado o eliminado el conector. Esta serie, que lleva comillas,designa la función que se utilizará. La función debe estar incluida en la DLL queacompaña al conector.

El campo Unloading_Function es el nombre de la función que debe llamarsecuando se vaya a descargar el conector. Tiene la siguiente signatura:

374 Programación con VisualAge RPG

Page 393: c 0924494

donde los parámetros son:

ppluginPath_La vía de acceso completa del conector invocado, incluyendo la barrainclinada invertida final.

ppluginStub_El resto del nombre del archivo del conector (por ejemplo, ″myplug.plg″).

pdllPath_La vía de acceso completa de la DLL que contiene los métodos expuestosde VARPG.

builderId_Serie utilizada por VARPG para identificar el constructor y por el conectoral comunicarse con el constructor.

remove_

0 El constructor se está apagando.

1 El usuario ha solicitado que se elimine todo el conector. En estecaso, el conector debería eliminar en este momento toda lainformación almacenada en el registro.

Valor de retorno

0 éxito

1 fallo o rechazo

Si el conector devuelve un 1 de esta función, el constructor puedepresentar al usuario la opción de eliminar obligatoriamente el conectordescargando su DLL. En este caso, es posible que el conector interrumpa elfuncionamiento del diseñador y deba volverlo a iniciar.

Unloading_Command_LineComo se ha mencionado más arriba, este campo no puede utilizarse al mismotiempo que el campo Unloading_Function.

Cuando se utiliza esta opción, se proporciona una serie para ejecutarla como si setratara de la línea de mandatos. Por ejemplo, se podría iniciar Netscapeespecificando la serie: netscape.exe

Este método permite obtener el mismo conjunto de parámetros que estaríandisponibles para una función en una DLL. Esto se consigue mediante la definiciónde variables de sustitución. Cuando se encuentra ’&0’, ’&1’, ’&2’, ’&3’, ’&4’ o ’&5’en la serie especificada, se sustituyen de la siguiente manera:

&0 ppluginPath_

&1 ppluginStub_

&2 pdllPath_

&3 builderId_

unsigned longunloadFunctionName(

const char* ppluginPath_,const char* ppluginStub_,const char* pdllPath_,const char* builderId_,int remove_)

Capítulo 25. Creación de conectores 375

Page 394: c 0924494

&4 remove_

&5 vía de acceso del directorio raíz del Diseñador GUI

IBM_PluginInterface | PluginInterfaceEs una función avanzada que no es necesaria. Este campo permite exponer elconector como componente programable. No se pueden utilizar estas dos opcionesen el mismo archivo .plg. Si no hay necesidad de especificar uno de estosparámetros, no lo haga.

Cuando se utiliza una de estas opciones, se empleará el nombre de la funciónespecificado cuando haya otros conectores que interactúen con este conectormediante una interfaz de destino/mandato/parámetros.

La signatura de la función debe ser:para la función de tipo IBM_, donde arguments_ se utiliza para entradas y salidas.

Para la función que no es de tipo IBM, la signatura debe ser:En este caso, si hay una serie de retorno, debería asignarse memoria a

ppreturnString_ mediante el conector con GlobalAlloc( GMEM_FIXED,[bufferSize]), para que VARPG pueda desasignar la memoria cuando hayaterminado con ella. Si no hay ninguna serie de retorno que sea necesaria, puedehacerse caso omiso de este parámetro. A continuación se muestra un ejemplo deeste mandato:

Para ver un ejemplo de conector que dé soporte a la función IBM_PluginInterface,consulte el ejemplo LPEXSAMP proporcionado en el directoriox:\adtswin\samples\vndplugs\lpexsamp (donde x corresponde a la letra de launidad en la que se ha instalado VisualAge RPG).

Begin_Details ... End_DetailsEntre estos códigos, entre el texto que desee mostrar al usuario cuando lainformación del conector se visualice en el recuadro de diálogo Gestionarconectores. Puede resultar útil dar una breve descripción del objetivo y del uso delconector. Se puede entrar el texto aquí o utilizar el formulario String/Residdescrito para mri.dll. Este campo es opcional, pero muy recomendado.

unsigned long __stdcall IBMtargetCommandFunction(const IString& pluginPath_,const IString& dllPath_,const IString& builderId_,const IString& target_,const IString& command_,IString& arguments_);

unsigned long __stdcall targetCommandFunction(const char* ppluginPath_,const char* pdllPath_,const char* pbuilderId_,const char* ptarget_,const char* pcommand_,const char* parguments_,char** ppreturnString_);

{IString returnString = ...;...

*ppreturnString = GlobalAlloc( returnString. length() + 1);strcpy( *ppreturnString, returnString);

}

376 Programación con VisualAge RPG

Page 395: c 0924494

Function_NameEs el nombre de la función que debe llamarse en conector.dll al activar el elementode menú. Se puede utilizar este campo o el campo Command_Line. No se puedenutilizar los dos. La signatura debería ser la siguiente:donde los parámetros son:

ppluginPath_Mismo significado que para unloadFunctionName().

pdllPath_Mismo significado que para unloadFunctionName().

builderId_Mismo significado que para unloadFunctionName().

menuContextId_Un valor entero largo sin signatura que representa el tipo de menú desdeel que se invoca este conector. Este valor determina el significado departsIds_. Los valores posibles son:

1 El conector se invoca desde la barra de menús (es decir, se trata deun conector pensado para proyectos) y partsIds_ es una serie vacía.

2 El conector se invoca para un único componente seleccionado, (esdecir, se trata de un conector pensado para una única selección) ypartsIds_ contiene el identificador del componente seleccionado.

4 El conector se invoca para un grupo de componentes seleccionadosconjuntamente, (es decir, se trata de un conector pensado para unaselección múltiple) y partsIds_ es una serie que contiene elconjunto delimitado por espacios en blanco de los identificadoresde los componentes seleccionados.

8 El conector se invoca cuando se inicia el diseñador GUI.

partsIds_

Es una serie que representa el componente o componentes a los que lallamada de función debería hacer referencia, según lo indicado enmenuContextId_. En partsIds_, cada identificador de componente es unasecuencia de valores enteros largos sin signatura separados por un punto(por ejemplo, 432.5632.612) que representan la jerarquía hijo-padre delcomponente en cuestión. En el ejemplo indicado, 612 es el ID delcomponente, 5632 es el ID de su padre y 432 es el ID del padre del padre.

Command_LineCuando se utiliza esta opción, se proporciona una serie para ejecutarla como si setratara de la línea de mandatos. Por ejemplo, se podría iniciar Netscapeespecificando la serie: netscape.exe.

Este método permite obtener el mismo conjunto de parámetros que estaríandisponibles para una función en una DLL. Esto se consigue mediante la definiciónde variables de sustitución. Cuando se encuentra ’&0’, ’&1’, ’&2’, ’&3’, ’&4’ o ’&5’en la serie especificada, se sustituyen de la siguiente manera:

unsigned longpluginFunctionName(

const char* ppluginPath_,const char* pdllPath_,const char* builderId_,unsigned long menuContextId_,const char* partsIds_);

Capítulo 25. Creación de conectores 377

Page 396: c 0924494

&0 ppluginPath_

&1 pdllPath_

&2 builderId_

&3 menuContextId_

&4 partsIds_

&5 vía de acceso del directorio raíz del Diseñador GUI.

Siguiendo el ejemplo anterior para Netscape, supongamos que el proveedorproporciona un archivo HTML con el conector y que este elemento de menú enparticular es para visualizar dicho archivo HTML. Supongamos también que elarchivo del conector se encuentra en d:\vendor\plugins y que el archivo HTML esd:\vendor\plugins\htmlsrc\plugpage.html. Para que el conector muestre estapágina web, la definición de la línea de mandatos podría ser la siguiente:netscape &0htmlsrc\plugpage.html

Que se ampliaría y ejecutaría como:netscape d:\vendor\plugins\htmlsrc\plugpage.html

Menu_NameEs una serie o un ID de recurso de serie que indica lo que el elemento de menúdebería ser. Estas series tienen el formato:submenú1/submenú2/.../submenúN/elementomenú

donde submenú1 hasta submenúN son submenús opcionales.

Por ejemplo:donde ″Plug-Me-In Inc.″ es el submenú y ″Who am I?″ es el elemento de menú.

Menu_Info_StringsEs una lista de series o de ID de serie que están asociados con los submenús oelementos de menú correspondientes, como se especifica en Menu_Name. Laasociación funciona a la inversa.

Por ejemplo, si se especifica un submenú y un elemento de menú en Menu_Name,pero sólo se especifica una serie en Menu_Info_Strings, la serie especificada enMenu_Info_Strings se asociará con el elemento de menú y se hará caso omiso delsubmenú. (Es posible que la adición de un elemento de menú anterior definierauna serie de área de información para el elemento de menú en cuestión.)

Supported_MenusComo se ha mencionado en Function_Name, menuContextId_ indica el tipo demenú. Supported_Menus indica los menús a los que debe añadirse esta entrada enparticular.

Help_IdSi se ha especificado un archivo de ayuda y hay ayuda asociada con este mandato,indique el ID de ayuda en el parámetro panel_largosin de Help_Id. Si seproporciona el parámetro_opcional_ventana_completa con un valor diferente a

Menu_Name: "Plug-Me-In Inc./Who am I?"

378 Programación con VisualAge RPG

Page 397: c 0924494

cero, la ayuda se visualizará en una ventana completa de ayuda, en lugar de en elárea emergente de contexto por omisión. Este campo adopta la forma de:y un ejemplo de codificación sería:

AcceleratorEste campo opcional especifica el acelerador que se asociará con el elemento.Consta de una de las teclas F1 a F12, seguida de uno o varios modificadores(SHIFT [DESPL], ALT, CONTROL)

Nota: <F1/10>, <Alt-F5/7/8/9/10> y <Despl-F9/10> ya están reservadas por eldiseñador y, si se especifican, no se tendrán en cuenta.

Para utilizar esta función, proporcione la siguiente información:Cuando se utilice este campo tendrá el siguiente aspecto:

End_of_DefinitionEste campo indica al analizador que ha finalizado una definición de función y quepuede empezar otra.

Plantilla de archivo .plg y ejemploAl utilizar los campos descritos anteriormente para crear un archivo .plg para elDiseñador GUI, hay que seguir este formato:

Nota: Debe haber al menos una definición de Function_Name o deCommand_Line. No hay límite en el número máximo permitido.

Help_Id: panel_largosin parámetro_opcional_ventana_completa

Help_Id: 1000 1

Accelerator: [F1 | F2 | F3 | ... | F12] [SHIFT] [CONTROL] [ALT]

Accelerator: F8 Shift

Capítulo 25. Creación de conectores 379

Page 398: c 0924494

Nota:v Todos los nombres de archivo son relativos a la ubicación del archivo .plg.v Los descargadores son opcionales, pero si se elige alguno, sólo se puede

haber uno de los dos.v Puede especificarse Function_Name o Command_Line.

A continuación se muestra un ejemplo específico de archivo .plg sencillo. ConVisualAge RPG se proporcionan algunos ejemplos de conectores. Estos archivos sepueden encontrar en el directorio X:\adtswin\samples\vndplugs\ de la estación detrabajo donde se ha instalado VisualAge RPG (X corresponde a la letra de launidad).

// Las líneas que empiezan por dos barras inclinadas no se tienen en cuenta// (es decir, se tratan como comentarios)

Alternate_Paths: serie_o_IDrecdll_Names: conector.dll mri.dllVendor_Name: serie_o_IDrecPlugin_Name: serie_o_IDrecHelp_File: archivo_ayuda.hlpUnloading_Function: "unloadingFunction"

(o bien)Unloading_Command_Line: "invocación línea mandatos con símb. de sust. &0, &1, &2,

&3, &4, &5"IBM_PluginInterface: "IBMtargetCommandFunction"

(o bien)PluginInterface: "targetCommandFunction"

Begin_Details:..Texto opcional que especifique la función del conector...

End_Details:

Function_Name: "nombreFunción1"(o bien)

Command_Line: "invocación1 línea mandatos con símb. de sust. &0, &1, &2,&3, &4"

Menu_Name: serie_o_IDrecMenu_Info_Strings: serie_o_IDrec serie_o_IDrec ...Supported_Menus: IDcontextoMenú1 IDcontextoMenú2 ...Help_Id: panel_largosin parámetro_opcional_ventana_completaAccelerator: [F1 | F2 | F3 | ... | F12] [SHIFT] [CONTROL] [ALT]End_of_definition:

380 Programación con VisualAge RPG

Page 399: c 0924494

Creación del archivo .EXEPara crear un archivo .EXE para el Diseñador GUI, hay que tener en cuenta que:

Cuando se utiliza VisualAge RPG para crear conectores, se utiliza el componente*component para que interactúe con el diseñador. Al definir los valores de losatributos PlugDLL, PlugId, PlugCmd, PlugRC y PlugResult, toda la informaciónnecesaria puede ser comunicada entre el diseñador y el conector.

Para crear un conector que funcione hay que establecer la comunicación adecuadaproporcionando al diseñador la siguiente información:

builderId_Es el mismo ID proporcionado por el diseñador cuando se invocó elconector.

target_Es una serie que representa el aspecto del diseñador con el que deseainteractuar.

command_Es la acción específica que desea que realice el diseñador.

parameters_Los argumentos necesarios para el mandato.

Nota: En un programa VARPG, builderId_ corresponde al atributo PlugId de*component. Para hacer una llamada a la interfaz del conector, antes hayque definir PlugId y PlugDLL. PlugDLL indica al módulo de tiempo deejecución de VARPG dónde se encuentra la dll que contiene la interfaz deconector del constructor. Al emitir un mandato, primero hay que concatenarlos valores de target_, command_ y parameters_ utilizando espacios enblanco como delimitadores y, a continuación, utilizar el resultado paradefinir el atributo PlugCmd de *component.

De retorno se obtiene un resultado y un código de error. En el caso de una llamadade función, uno de los parámetros está definido para contener la serie delresultado y el valor entero largo sin signatura devuelto contiene el código de error.A continuación se especifican algunos códigos de retorno básicos comunes paratodos los mandatos. Los códigos de error adicionales se definirán en la tablacorrespondiente de destinos y mandatos.

// Conector para proyecto de impresión

Vendor_Name: "Plug-Me-In Inc."Plugin_Name: "Who Am I?"Begin_Details:

Who Am I?

Este conector muestra información acerca del proyectoen uso, incluido el nombre del directorio y del archivo.

End_Details:

Command_Line: "d:\myproj\whoami\rt_win32\whoami.exe &1 &2 &4"Menu_Name: "Plug-Me-In Inc./Who am I?"Supported_Menus: 1Accelerator: F7 ShiftEnd_of_Definition

Capítulo 25. Creación de conectores 381

Page 400: c 0924494

Código de retornoSignificado

0 Todo ha ido bien y el mandato se ha ejecutado.

1 No se ha reconocido el destino.

2 El destino no ha reconocido el mandato.

4 No se puede encontrar el constructor.

5 Se ha producido un error desconocido y los resultados del mandato no sonfiables.

Destinos y mandatos y los valores de retorno asociadosA continuación se muestra una lista de los destinos y mandatos válidos, junto conla semántica de sus parámetros y los valores de retorno.

Tabla 13. Destino: Proyecto

Mandato Parámetro(s) Significado/Valor de retorno

Build [win32|java]Valor por omisión: win32

Construye una versión win32 ojava del proyecto, dependiendode si la plataforma es ″win32″ o″java″. Sin valor de retorno;retorno inmediato (es decir, antesde finalizar la construcción).

BuildOptions [win32|java]Valor por omisión: win32

Muestra las opciones de laconstrucción para win32 o Java,dependiendo de si la plataformaes ″win32″ o ″java″. Sin valor deretorno, pero no hay retornohasta que no se haya cerrado elrecuadro de diálogo (modal).

CursoredPart ninguno Devuelve una serie que contieneel identificador del componenteen el que se encuentra el cursor.Si no hay ninguna ventana dediseño abierta o si ningunaventana de diseño abierta es laventana de diseño activa, estaserie estará vacía.

ExpandAll [1] Si el parámetro es igual a 1, seexpandirá toda la vista de árbol;en caso contrario, estarácontraída.

ForceOpen [Nombreproyecto] Abre el proyecto especificado sincomprobar si el proyecto en usotiene que guardarse. Devuelveun 1 para indicar que el mandatoForceOpen ha sido satisfactorio oun 0 para indicar que ha sidoinsatisfactorio.

382 Programación con VisualAge RPG

Page 401: c 0924494

Tabla 13. Destino: Proyecto (continuación)

Get ProjectDir Devuelve el directorio raíz delproyecto en uso.

ProjectFileName Devuelve el nombre completodel archivo .IVG del proyecto enuso.

ProjectTargetName Devuelve el nombre del archivoque se generará cuando seconstruya el proyecto (porejemplo, ″myproj.exe″).

ProjectTitle Devuelve el título del proyectoen uso.

ProjectFileStub Devuelve el nombre de archivo(menos la extensión) de losnombres del proyecto en uso(por ejemplo, ″myproj″).

IsSaveRequired ninguno Devuelve 1 para indicar que seha modificado el proyecto y 0para indicar que no se harealizado ningún cambio desdeque se abrió.

IsTemporary ninguno Devuelve 1 si se trata de unproyecto sin nombre y 0 en casocontrario.

MostRecentlyUsed n Devuelve el enésimo proyectoabierto más recientemente, donden es igual o superior a 1.Devuelve una serie vacía si elíndice está fuera de límites.

Open nombreProyecto Comprueba si el usuario deseaguardar el proyecto antes deabrir otro. Devuelve 1 si elproyecto se ha abiertosatisfactoriamente y 0 en casocontrario.

Capítulo 25. Creación de conectores 383

Page 402: c 0924494

Tabla 13. Destino: Proyecto (continuación)

PartId nombreComponente[nombreVentana|[0|1|2]]

Devuelve un ID de componentecuando se da un nombre decomponente. Si se especifica unnombre de ventana, se devolveráel ID del componente o, si nohay dicho componente, sedevolverá una serie vacía. Si seespecifica un tipo de búsqueda,se utilizarán las siguientes reglascuando se busque uncomponente con el nombre dado:0 (valor por omisión)- Devolver el primercomponente con el

nombre dado.1 - Devolver todos los

componentes conel nombre dado.2 - Si sólo hay uncomponente con estenombre, debe devolverse;en caso contrario, no debedevolverse nada.

PromptedSave ninguno Solicita al usuario el nombre delproyecto y guarda el proyecto.Devuelve un 1 para indicar quese ha guardado el proyectosatisfactoriamente; en casocontrario, devuelve un 0.

PromptExisting ninguno Solicita al usuario un proyectoexistente. Devuelve el nombre dearchivo del proyecto.

Run ninguno Ejecuta el proyecto en uso.

Save ninguno Guarda el proyecto en uso.

SaveAs nombreProyecto Guarda el proyecto en uso con elnombre de proyecto especificado.

SelectedParts ninguno Devuelve una serie que contienelos identificadores de todos loscomponentes seleccionados en lavista de árbol del proyecto.

Tabla 14. Destino: PartClass

Mandato Parámetro(s) Significado/Valor de retorno

AllAttributes ClassName Devuelve una lista de losatributos soportados por elnombre de la clase especificada.

AllClasses ninguno Devuelve una lista de todas lasclases de componentesdisponibles. Cada elemento de lalista va entre comillas dobles, yaque algunos de ellos puedenconstar de varias palabras (porejemplo, los componentes deproveedor).

384 Programación con VisualAge RPG

Page 403: c 0924494

Tabla 14. Destino: PartClass (continuación)

AllEvents ClassName Devuelve todos los eventosregistrados de la claseespecificada.

IBMClasses ninguno Devuelve una lista de todas lasclases de componentessuministradas por IBM que nosean de proveedores.

IconDll ClassName Devuelve la vía de acceso de ladll que contiene el icono querepresenta la clase decomponente especificada.

IconId ClassName Devuelve el ID de recurso delicono (en la dll especificada por″IconDll″) de la claseespecificada.

IsType NombreTipo Devuelve 1 para indicar que laclase especificada enNombreClase es del tipoespecificado; en caso contrario,devuelve 0. Los posibles valoresde NombreTipo son: Frame,Canvas, MenuBar, NoteBook,NoteBookPage, PopUpMenu,SubMenu, MenuItem, Subfile ySubfileEntryField.

VendorClasses ninguno Devuelve una lista de todas lasclases de componentes deproveedores disponibles.

Tabla 15. Destino: Componente

Mandato Parámetro(s) Significado/Valor de retorno

ActionSubroutine IDComponente nombreEvento Localiza la subrutina de la acciónenlazada, el nombreEvento o creaun enlace y lo explora en caso deque no exista.

ActionSubroutines IDComponente Devuelve una lista de subrutinasde acción definidas para estecomponente.

AllEvents IDComponente Devuelve todos los eventosregistrados del componenteespecificado.

Children [IDComponente] Devuelve una lista de ID decomponente delimitados porespacios en blanco que muestratodos los hijos del componenteespecificado. Si no seproporciona ningúnIDComponente, se devuelve unalista de todas las ventanas delproyecto.

ClassName IDComponente Devuelve el nombre de clase delcomponente indicado.

Capítulo 25. Creación de conectores 385

Page 404: c 0924494

Tabla 15. Destino: Componente (continuación)

CreateChild IDComponente nombreClase Crea un componente del nombrede clase especificado como hijodel componente indicado.Devuelve el IDComponente delcomponente recién creado.

CreateFrame ClassName Crea un componente de la claseespecificada. La clase debe ser uncomponente basado en marcos.Devuelve el IDComponente delcomponente recién creado.

DataInfo dataType dataLengthdecimalPlaces

donde:

dataType indica un valor’0’=Numérico o bien ’1’=Carácter

dataLength expresa la longitudde los datos

decimalPlaces indica el númerode posiciones decimales

Devuelve una serie de tresnúmeros, separados entre ellospor espacios en blanco. Loscomponentes relacionados son,entre otros, el campo de entrada,el texto estático y el campo deentrada de subarchivo.

ExtraColorAreasVer Nota más abajo

IDComponente Devuelve el número de áreas decolor soportadas por elcomponente, en caso de que elcomponente soporte áreas decolor aparte del primer plano yel fondo.

FileName IDComponente Obtiene el nombre de archivodefinido para este componente.Si el componente no soportaarchivos, el valor de retorno esuna serie vacía.

GetColor IDComponente [x]donde x corresponde al área decolor del componente indicado.

Obtiene el color del áreaespecificada. Devuelve una seriecon 4 números delimitados porespacios en blanco:useDefault - (0 ó 1)redMix - (0 - 255)greenMix - (0 - 255)blueMix - (0 - 255)

386 Programación con VisualAge RPG

Page 405: c 0924494

Tabla 15. Destino: Componente (continuación)

GetFont IDComponente [x]donde x corresponde al área defont del componente indicado.

Obtiene el font del componente.Devuelve una serie vacía si elfont no está soportado. En casocontrario, la primera parte de laserie devuelta es un 0 o un 1,indicando si se utiliza o no elfont por omisión; la segundapalabra de la serie es el cuerpo;la tercera palabra de la serie esun número que reúne estilos defont aplicables de entre:1 - negrita2 - cursiva4 - subrayado8 - tachado16 - contornoEl resto de la serie es el nombredel tipo de letra.

GetRect IDComponente Obtiene las coordenadas (x yancho alto) del componente conrelación a su padre.

HasFile IDComponente Devuelve un 1 para indicar queel componente soporta unarchivo (por ejemplo, lienzo,imagen, medios, etc.); en casocontrario, devuelve un 0.

IsColorAreaVer Nota más abajo

IDComponente [x]donde x corresponde al área decolor del componente indicado.

Devuelve un 1 para indicar queel área de color está soportada;en caso contrario, devuelve un 0.

IsFontArea IDComponente [x]donde x corresponde al área defont del componente indicado.

Devuelve un 1 para indicar queel área de font está soportada; encaso contrario, devuelve un 0.

Label IDComponente Devuelve la etiqueta delcomponente (si existe).

LinkedEvents IDComponente Devuelve una lista de eventospara los que este componentetiene enlaces de acción.

Name IDComponente Devuelve el nombre delcomponente tal como se muestraen la vista de árbol y en elcuaderno de configuración.

OpenDesignWindow IDComponente [1] Cuando se asigna el valor 1, abrey activa la ventana de diseño a laque pertenece el componenteindicado. Si se asigna el valor de0, se cerrará la ventana dediseño.

OpenPart IDComponente Abre el cuaderno deconfiguración del componente o,si el componente es un marco,abre la ventana de diseñocorrespondiente al componente.

OpenSettings IDComponente Abre el cuaderno deconfiguración del componente.

Capítulo 25. Creación de conectores 387

Page 406: c 0924494

Tabla 15. Destino: Componente (continuación)

SetColorVer Nota más abajo

IDComponentecolorAreauseDefaultredMixgreenMixblueMix

Define el color del áreaespecificada. Consulte GetColorpara obtener más informaciónacerca de los valores permitidospara cada parámetro.

SetCursored IDComponente Si la ventana de diseño delcomponente está abierta, elcomponente pasa a ser elcomponente activo, pero elestado de la selección no varía. Sila ventana de diseño no estáabierta, no tiene ningún efecto.

SetDataInfo partId dataType dataLengthdecimalPlaces

donde:

partId es el ID de componente

dataType indica un valor’0’=Numérico o bien ’1’=Carácter

dataLength expresa la longitudde los datos

decimalPlaces indica el númerode posiciones decimales

Establece las propiedades de losdatos de un componente. Noactualiza el cuaderno depropiedades de un componenteque ya esté abierto o siendoutilizado. El programador debeasegurarse de que los nuevosvalores son compatibles con losvalores previamente existentesque ya se han definido para elcomponente. Los componentesrelacionados son, entre otros, elcampo de entrada, el textoestático y el campo de entrada desubarchivo.

SetFileName IDComponentenombreArchivoNuevo

Define el nombre de archivo paraeste componente. No tieneningún efecto si el componenteno soporta archivos.

SetFont partId fontArea setToDefaultpointSize styles faceName

Define el font del componente.

SetLabel IDComponente etiquetaNueva Intenta definir la etiqueta delcomponente. Si la etiquetaespecificada no es válida, apareceun mensaje de error. Devuelveun 1 para indicar que se hadefinido la etiqueta; en casocontrario, devuelve un 0.

SetName IdComponente nombreNuevo Intenta definir el nombre delcomponente. Si no es posiblehacerlo, aparece un mensaje deerror. Si el componente tieneenlaces de acción asociados,aparece un mensaje preguntandoal usuario si desea romperlos.Devuelve un 1 para indicar queel resultado ha sido satisfactorioo un 0 en caso contrario.

SetRect IDComponente x y ancho alto Define las coordenadas (x yancho alto) del componente conrelación a su padre.

388 Programación con VisualAge RPG

Page 407: c 0924494

Tabla 15. Destino: Componente (continuación)

SetSelected IDComponente [0|1] [0|1] Selecciona/deselecciona elcomponente especificado. Elprimer parámetro de la serie esactivar y el segundo es exclusivo.Si no se especifica activar oexclusivo, se entiende que tienenel valor de ″1″. Exclusivo indicasi la selección del componentedebe deseleccionar el resto decomponentes y activar indica sidebe modificarse el estado deselección del componente.

SetStyles IDComponente estilosestilosAmpliados [0|1]

Define los estilos y los estilosampliados del componenteespecificado. Observe que estosvalores no se actualizaránnecesariamente en el cuadernode propiedades de la ventana dediseño si alguna de ellas estáabierta. Este mandato estápensado para cuando se crea einicializa un componente. Un ″0″al final de esta serie indica que elvalor está expresado en formatodecimal, mientras que un 1indica que se utiliza la notaciónhexadecimal.

Styles IDComponente [0|1] Devuelve dos valores numéricosseparados por un espacio querepresentan los estilos y losestilos ampliados delcomponente especificado. Un ″0″al final de esta serie indica que elvalor está expresado en formatodecimal, mientras que un 1indica que se utiliza la notaciónhexadecimal.

Zoom IDComponente [0|1] Amplía la vista de árbol y sedesplaza al componenteindicado. Si se especifica un ″1″,también se activa la vista deárbol.

Nota: Los componentes pueden tener un área de color de primer plano (1), defondo (0), no tener área de color o tener áreas de color adicionales. Lasventanas, por ejemplo, no tienen áreas de color. Los recuadros de seleccióntienen áreas de color de primer plano y de fondo. Los gráficos tienen áreasde color adicionales. Por tanto, 0 y 1 sólo indican necesariamente el color deprimer plano y de fondo si el componente no tiene colores adicionales.

Capítulo 25. Creación de conectores 389

Page 408: c 0924494

Los siguientes mandatos requieren que el archivo fuente esté abierto en LPEX.

Tabla 16. Destino: Subrutina

Mandato Parámetro(s) Significado/Valor de retorno

DeleteActionSub nombreRutina Suprime la subrutina de accióncon el nombre especificado.

DeleteUserSub nombreRutina Suprime la subrutina de usuariocon el nombre especificado.

UserSubroutine nombreRutina Si la subrutina no existe, creauna subrutina de usuario con elnombre especificado y la ubicaen el archivo fuente. Si existe, seubica en el archivo fuente.

UserSubroutines ninguno Devuelve una lista de lassubrutinas de usuario.

Tabla 17. Destino: Cuadrícula

Mandato Parámetro(s) Significado/Valor de retorno

IsOn ninguno Devuelve un 1 si la cuadrículaestá activada y un 0 si estádesactivada.

TurnOn [0|1] Si se asigna el valor 1, se activarála cuadrícula. Si se asigna elvalor de 0, se desactivará. (Elvalor por omisión es activado.)

Tabla 18. Destino: Lpex

Mandato Parámetro(s) Significado/Valor de retorno

DoIt Cualquier_mandato_LPEX Pasa los parámetros a ″DoIt″ deLPEX.

IsSourceFileOpen ninguno Devuelve un 1 para indicar queel archivo fuente está abierto; encaso contrario, devuelve un 0.

OpenSourceFile ninguno Abre el archivo fuente en LPEX.

Query Cualquier_consulta_LPEX Pasa los parámetros a ″Query″ deLPEX.

Tabla 19. Destino: Conector

Mandato Parámetro(s) Significado/Valor de retorno

AddPlugin nombreArchivo Intenta añadir el conectorespecificado. Devuelve ″0″ si elresultado es satisfactorio.

390 Programación con VisualAge RPG

Page 409: c 0924494

Tabla 19. Destino: Conector (continuación)

get númeroConectores Devuelve el número deconectores instalados.

conector índiceBasadoUno Devuelve la vía de accesocompleta del conector que ocupael lugar índiceBasadoUno. Si n esmenor que 1 o mayor que elnúmero de conectores, sedevuelve una serie nula.

conectores Devuelve una lista de las vías deacceso completas de todos losconectores.

InvokePlugin índiceBasadoUno destinomandato parámetros

Invoca el conector utilizando unainterfaz destino/mandato.

Tabla 20. Destino: Registro

Mandato Parámetro(s) Significado/Valor de retorno

DeleteKey clave Este mandato suprimirá la claveespecificada del registro(incluidas las subclaves).

Get clave [″valorOmisión″] Si no existe la clave, el valor deretorno es el valor por omisión;en caso contrario, es el valor dela clave en el registro. Cuandoentre los datos, sustituya la serie’valorOmisión’ por la serie quedesee. Las comillas dobles sonnecesarias.

GetRect clave [″x y ancho alto″] Este mandato recuperará unrectángulo del registro y, si no seencuentra el elemento con laclave especificada, se devolveránlos valores por omisiónsuministrados. Las comillasdobles son necesarias.

Set clave valor Utilice este mandato para definirel valor de una serie en elregistro. No hay valor de retorno.

SetRect clave ″x y ancho alto″ Este mandato almacenará elrectángulo especificado en elregistro utilizando coordenadasnormalizadas. Las comillasdobles son necesarias.

Nota acerca de cómo utilizar los mandatos del registro.

Es muy recomendable que los conectores utilicen una subclave inicial queprobablemente sea exclusiva, con el fin de que no interfieran con las entradas en elregistro de otros conectores.

Todas las entradas del registro creadas con estos mandatos estarán restringidas auna subsección común de la entrada de registro de VARPG; sin embargo, esposible solapar conectores.

Capítulo 25. Creación de conectores 391

Page 410: c 0924494

Para evitar que se solapen, los conectores pueden utilizar una variación delnombre de la vía de acceso del archivo .PLG como subclave inicial, de la siguientemanera:

Si el nombre de la vía de acceso del conector es:"c:\plugins\My_Plugins\myplug.plg",

y la entrada del registro debe utilizarse para almacenar la posición de una ventana,una clave adecuada para este valor sería:"c__plugins_my plugins_myplug.plg\Posición ventana"

(Observe que se han eliminado las mayúsculas de la parte correspondiente a la víade acceso de la clave y que los dos puntos y las barras inclinadas invertidas se hanconvertido en caracteres de subrayado.) Las claves y los valores especificadosdeben ir entre comillas, ya que las claves pueden contener espacios. Por lo tanto, sideseara definir el valor de una serie, debería utilizar:Set( "c__plugins_my_plugins_myplug.plg\Nombre clave relevante" "El valor nuevo.")

Las comillas incorporadas deben ir precedidas de una barra inclinada invertida:Set( "c__plugins_my_plugins_myplug.plg\Nombre clave relevante"

"El valor \"entre comillas\"nuevo.")

Hay otros mandatos que son aplicables a algunas de las propias ventanasconstituyentes del Diseñador GUI. (Por ejemplo, el catálogo de componentes.)

Destinos aplicables:MainWindow

Es la ventana principal del Diseñador GUI.Catalog

El catálogo de componentes.DBRefDlg

La ventana Definir campos de referencia.ImportDlg

La ventana Importar archivo de pantalla.LPEX La ventana del editor.

Observe que estos mandatos sólo son aplicables cuando la ventana especificadaestá abierta.

Tabla 21. Destino: Ventanas constituyentes del Diseñador GUI

Mandato Parámetro(s) Significado/Valor de retorno

GetHandle ninguno Devuelve el HANDLE deWindows de la ventanaespecificada.

GetIWindowPointer ninguno Devuelve el puntero de IWindowde la ventana especificada.

MoveSizeTo X Y ancho alto Define el tamaño y la posición dela ventana.

MoveTo X Y Desplaza la ventana a la posición(X, Y).

Position ninguno Devuelve la posición de laventana en la forma ″X, Y″.

392 Programación con VisualAge RPG

Page 411: c 0924494

Tabla 21. Destino: Ventanas constituyentes del Diseñador GUI (continuación)

Rect ninguno Devuelve el rectángulo de laventana en la forma ″X, Y, ancho,alto″

SetFocus ninguno Activa la ventana indicada.

SetSize ancho alto Define el tamaño de la ventana.

ShowSetFocus ninguno Muestra la ventana (en caso deque no esté visible) y la activa.

Size ninguno Devuelve el tamaño de laventana en la forma ″X, Y″.

NotifyOnClose Handle de ventana Especifica la ventana a la quedebe notificarse que se cierra elDiseñador GUI.

Ejemplo de código fuente de conectorA continuación se muestra el código fuente del conector que corresponde alarchivo plg utilizado en la sección anterior.

********************************************************************** ** Program ID . . : WhoAmi ** ** Description . : Sample program to illustrate the Vendor plugin ** interface of VARPG. ** ** When invoked from the Vendor menu item on the ** GUI Designer this program will use the plugin ** interface to gather information about the ** current project and display it on a window ** named MAIN. ** ** The following plugin file, WHOAMI.PLG, was specified when adding ** this plugin to the GUI designer ** ** // WhoAmi.plg plug in file ** Vendor_Name: "Plug-Me-In Inc." ** Plugin_Name: "Who Am I?" ** Begin_Details: ** Who Am I? ** This plug-in will display information about the current ** project including its directory name and file name. ** End_Details: ** Command_Line: "d:\myproj\whoami\rt_win32\whoami.exe &1 &2"** Menu_Name: "Plug-Me-In Inc./Who am I?" ** Supported_Menus: 1 ** Accelerator: F7 Shift ** End_of_Definition ** ***********************************************************************

D Cmd S 255A*

C *Entry PlistC Parm PlugDLL 64C Parm PlugID 64

Capítulo 25. Creación de conectores 393

Page 412: c 0924494

********************************************************************** ** Ventana . : Main ** ** Componente : PB_Cancel ** ** Evento . . : Press ** ** Descripción: Terminar el programa ** ***********************************************************************

C PB_CANCEL BEGACT PRESS MAIN*

C Move *on *inlr*

C ENDACT*********************************************************************** ** Ventana . : Main ** ** Componente : Main ** ** Evento . . : Create ** ** Description: Set up the PLUGDLL and PLUGID values of the ** *COMPONENT part to establish communication with the ** GUI builder. ** ** Execute PLUGCMD attributes to collect information ** about the current project ** ***********************************************************************

C MAIN BEGACT CREATE MAIN*

C '*Component' Setatr PlugDll 'PlugDLL'C '*Component' Setatr PlugID 'PlugID'*

C Eval Cmd='Project Get ProjectDir'C '*Component' Setatr Cmd 'PlugCmd'C '*Component' Getatr 'PlugResult' DirName*

C Eval Cmd='Project Get ProjectFileStub'C '*Component' Setatr Cmd 'PlugCmd'C '*Component' Getatr 'PlugResult' File*

C Eval Cmd='Project Get ProjectTargetName'C '*Component' Setatr Cmd 'PlugCmd'C '*Component' Getatr 'PlugResult' TAR

*C Eval Cmd='Project Get ProjectTitle'C '*Component' Setatr Cmd 'PlugCmd'C '*Component' Getatr 'PlugResult' Title*

C Eval Cmd='Project Get ProjectFileName'C '*Component' Setatr Cmd 'PlugCmd'C '*Component' Getatr 'PlugResult' Folder*

C Write 'Main'*

C ENDACT

394 Programación con VisualAge RPG

Page 413: c 0924494

Empaquetado de la aplicaciónEl paso final de la creación del conector es la compilación del archivo .EXE.Seleccione Construir en el menú desplegable Archivo y, a continuación, laplataforma en la que desea utilizar el conector. Una vez que el archivo estécompilado, ya estará listo para utilizarlo. Consulte las instrucciones de Adición deconectores de proveedor para añadir el conector. A partir de este punto, ya puedeutilizar el conector o realizar las pruebas que sean necesarias.

Consideraciones al crear conectores con VisualAge para C++El proceso de creación de conectores con VisualAge para C++ es el mismo quepara VisualAge RPG. La única diferencia es que cuando se crea el conector conVisualAge para C++, el programador no tiene el uso directo del componente*component. Para permitir que los programas de VisualAge para C++ puedanutilizarse como conectores, se proporciona la función IBMExecuteVDECommand().Su uso se muestra en el conector de ejemplo ″TreeSamp″.

En caso de que sea necesario, se puede cortar y pegar el código de los directoriosx:\adtswin\samples\vndplugs\treesamp (donde x corresponde a la letra de launidad de instalación de VisualAge RPG) yx:\adtswin\samples\vndplugs\plugutil para crear las llamadas correctas a lafunción IBMExecuteVDECommand().

Consideraciones al crear conectores con REXXEl proceso de creación de conectores con REXX es casi idéntico al del ejemplo deVisualAge RPG. Los programadores de REXX no tienen acceso directo al DiseñadorGUI que utiliza el componente *component. Para facilitar el uso de scripts REXXcomo conectores, se incluye la función RexxExecuteVDECommand() entre esteconjunto de funciones. En el conector de ejemplo ″RexxSamp″ se incluye unejemplo de cómo utilizar esta función en un archivo REXX.

En caso de que sea necesario, se puede cortar y pegar el código del directoriox:\adtswin\samples\vndplugs\rexxsamp (donde x corresponde a la letra de launidad de instalación de VisualAge RPG) para crear las llamadas correctas a lafunción REXXExecuteVDECommand().

Capítulo 25. Creación de conectores 395

Page 414: c 0924494

396 Programación con VisualAge RPG

Page 415: c 0924494

Parte 5. Distribución de la aplicación“Capítulo 26. Cómo empaquetar el código de tiempo de ejecución y lasaplicaciones” en la página 399

Describe cómo utilizar el programa de utilidad de empaquetado.

“Capítulo 27. Instalación del código de tiempo de ejecución y las aplicacionespara Windows NT/95/98” en la página 407

Describe cómo utilizar el programa de utilidad de instalación paraaplicaciones Windows NT/95/98.

© Copyright IBM Corp. 1994, 2000 397

Page 416: c 0924494

398 Programación con VisualAge RPG

Page 417: c 0924494

Capítulo 26. Cómo empaquetar el código de tiempo deejecución y las aplicaciones

Después de construir y probar la aplicación, puede empaquetarla y distribuirla aotras estaciones de trabajo que tengan el código de tiempo de ejecución deVisualAge RPG instalado.

Esta sección describe cómo empaquetar el código de tiempo de ejecución deVisualAge RPG y las aplicaciones de VisualAge RPG

Nota: Si la aplicación va a utilizar un servidor AS/400 distinto de aquél al que seaccedió durante el ciclo de desarrollo, todos los objetos de AS/400 utilizadospor la aplicación también deben empaquetarse y restaurarse en el nuevoservidor. La herramienta de empaquetado de aplicaciones VisualAge RPG nolos empaqueta.

Antes de empezarAsegúrese de que los archivos que la aplicación necesita se almacenan en eldirectorio de tiempo de ejecución adecuado (RT_WIN32 para Windows NT/95/98o RT_JAVA para Java;). Algunos archivos se colocan automáticamente en eldirectorio de tiempo de ejecución después de construir la aplicación (por ejemplo,los archivos ·MSG, ·HLP, ·DLL, ·BND, ·RST y ·EXE); otros deberá colocarlos ustedmismo (por ejemplo, ·BMP, ·GIF,·ICO, ·JPG,·MID, y ·WAV).

Si coloca archivos adicionales en los directorios de tiempo de ejecución antes deempaquetar la aplicación, asegúrese de que los nombres de archivo no sean losmismos que los de los archivos de aplicación existentes.

Después de colocar todos los archivos en el directorio de tiempo de ejecución,asegúrese también de que no haya dos archivos que tengan el mismo nombre y deque no se dé ninguna coincidencia en los dos primeros caracteres de su extensiónde archivo. Por ejemplo, si tiene dos archivos FILEA·ABC y FILEA·ABB en eldirectorio RT_WIN32, uno se sobregrabará durante el proceso de empaquetado.

Si desea empaquetar en disquetes, conviene tener disquetes preformateadosdisponibles antes de empezar el proceso de empaquetado.

Cómo empaquetar el código de tiempo de ejecución y las aplicacionesde VisualAge RPG

En esta sección se describe el proceso que debe seguir para empaquetar el códigode tiempo de ejecución de VisualAge RPG, una aplicación o componentescompartidos.

Nota: Verifique que el nombre de ubicación remota en el archivo RST es el mismoservidor que utilizarán los usuarios. De lo contrario, modifique la columnaUbicación remota para la entrada en la página Servidores del cuadernoDefinir información de AS/400. Para acceder a este cuaderno desde elDiseñador GUI, seleccione Definir información de AS/400 del menú

© Copyright IBM Corp. 1994, 2000 399

Page 418: c 0924494

desplegable Servidor. Para acceder en el tiempo de ejecución, utilice el iconoDefinir información de AS/400. Para acceder en tiempo de empaquetado,utilice el botón Cambiar servidor.

En el archivo RST, también debe especificar el protocolo correcto utilizado por losusuarios.

Para SNA, el nombre de ubicación remota es el nombre del direccionador definidoen Client Access.

Para TCP/IP, el nombre de ubicación remota es el nombre de sistema principalAS/400 definido en la lista de servidores TCP/IP.

Inicio de la herramienta de empaquetadoPara iniciar la herramienta de empaquetado utilice uno de estos métodos:v Seleccione Proyecto>Empaquetar del Organizador de proyectos.v Seleccione la opción Empaquetar del menú emergente del icono de proyecto.v Seleccione Herramienta de empaquetado de aplicaciones del menú

Inicio>Programas>VisualAge RPG y CODE400>VisualAge para RPG.

Aparecerá la ventana Empaquetar aplicación:

Especifique el sistema de destino de la aplicación:v Windows NT/95/98

Empaqueta la versión Windows de su aplicación para la plataforma WindowsNT/95/98.

v Aplicaciones Java para Windows NT/95/98

Empaqueta la versión Java de su aplicación para la plataforma WindowsNT/95/98.

v Aplicación/applet Java para todas las plataformas

Empaqueta la versión Java de su aplicación para otros sistemas operativos.

400 Programación con VisualAge RPG

Page 419: c 0924494

Cómo empaquetar aplicaciones Windows para WindowsNT/95/98

Seleccione Windows NT/95/98 y pulse Aceptar. Aparece el diálogo Ventana deempaquetado:

Especifique lo siguiente:v Lo que se desea empaquetarv La información de empaquetado de la aplicaciónv La información de empaquetado del tiempo de ejecución

Especificación de lo que se desea empaquetarEn la ventana Empaquetar especifique la información siguiente:

Nombre de aplicaciónEl nombre del proyecto de aplicación totalmente calificado. Puede escribirencima del valor por omisión (si lo hay) o utilizar el pulsador Buscar parainvocar la ventana Buscar proyectos para empaquetar. Cuando se especificaun nombre de proyecto de aplicación, se visualiza el título de la aplicacióncon carácter informativo.

Lo que se desea empaquetarUtilice los recuadros de selección para indicar si desea empaquetar laaplicación, los componentes compartidos, el código de tiempo de ejecucióno los tres elementos. Si se seleccionan componentes compartidos, se abriráuna ventana con una lista de los componentes compartidos. Se puedenseleccionar los componentes compartidos de la lista que se deseanempaquetar.

Utilice los botones de selección para indicar si desea empaquetar toda laaplicación o sólo los componentes seleccionados. Si elige empaquetarcomponentes seleccionados, se abrirá una ventana con una lista decomponentes de la aplicación que pueden seleccionarse. También se

Capítulo 26. Cómo empaquetar el código de tiempo de ejecución y las aplicaciones 401

Page 420: c 0924494

pueden empaquetar componentes compartidos adicionales creados conotras aplicaciones. Estos componentes compartidos se añadiránautomáticamente a la lista la próxima vez que elija empaquetar porcomponentes.

Especificación de la información de empaquetado de laaplicaciónUna vez haya finalizado sus selecciones en la ventana de empaquetado, pulseAceptar. Aparece la ventana de información sobre el empaquetado:

En la ventana Información de empaquetado, especifique la información siguiente:

Directorio destinoEl directorio destino para el empaquetado. Si se empaqueta en un disquete,el directorio destino sólo puede ser el directorio raíz del disquete: nopuede haber ningún subdirectorio. Si empaqueta en un directorio, esedirectorio no debe contener otros archivos.

Nombre de la compañíaEl nombre de la compañía con el que se registrará la aplicación.

Nota: Cuando empaquete una versión actualizada de una aplicacióndistribuida con anterioridad, utilice el mismo nombre de compañíapara la aplicación revisada. De lo contrario, la aplicación revisadaserá tratada como si fuera nueva.

VersiónLa versión de la aplicación.

Título El título de la aplicación.

402 Programación con VisualAge RPG

Page 421: c 0924494

Aquí puede utilizar el botón Cambiar servidor para visualizar una lista deservidores (ubicaciones remotas) utilizados por su aplicación. Puede modificar lalista para que el paquete utilice los nuevos nombres.

Seleccione Empaquetar para iniciar el empaquetado. Aparece una ventana deindicador de progreso. Se visualizan mensajes para indicar al usuario las etiquetasque debe poner en los diversos disquetes a medida que los crea. Cuando se hacompletado el empaquetado, se visualiza un mensaje de realización.

Cómo especificar la información de empaquetado del tiempo deejecuciónSi ha especificado que desea empaquetar el código de tiempo de ejecución, debeespecificar el directorio destino en la ventana Empaquetar tiempo de ejecución:

Si se empaqueta en un disquete, el directorio destino sólo puede ser el directorioraíz del disquete: no puede haber ningún subdirectorio. Si empaqueta en undirectorio, ese directorio no debe contener otros archivos.

Seleccione Empaquetar para iniciar el empaquetado. Aparece una ventana deindicador de progreso. Un mensaje le indicará que el proceso se ha completado.

Cómo empaquetar aplicaciones Java para Windows NT/95/98El empaquetado de la versión Java de su aplicación para la plataforma WindowsNT/95/98 sigue un proceso similar al de la versión de Windows.

Especifique lo que desea empaquetar y si desea empaquetar el tiempo deejecución. Si desea empaquetar la aplicación, especifique el nombre del proyecto deaplicación y seleccione el recuadro de selección de la aplicación. Utilice el recuadrode selección de tiempo de ejecución para empaquetar el tiempo de ejecución.

Capítulo 26. Cómo empaquetar el código de tiempo de ejecución y las aplicaciones 403

Page 422: c 0924494

Cómo empaquetar aplicaciones Java para otras plataformasSeleccione Aplicación/applet Java para todas las plataformas en la ventanaEmpaquetar aplicación y pulse Aceptar. Aparece la ventana Empaquetar Java:

Especifique lo siguiente:v Especifique lo que desea empaquetar: la aplicación, el tiempo de ejecución o

ambos.v El formato de su paquete: los archivos de aplicación (sólo válidos si elige

Aplicación) o bien el archivo Jar.

Especificación de lo que se desea empaquetarEn la ventana Empaquetar Java especifique la siguiente información:

Nombre de aplicaciónEl nombre del proyecto de aplicación totalmente calificado. Puede escribirencima del valor por omisión (si lo hay) o utilizar el pulsador Buscar paravisualizar la ventana Buscar proyectos para empaquetar. Cuando seespecifica un nombre de proyecto de aplicación, se visualiza el título de laaplicación con carácter informativo.

Lo que se desea empaquetarIndique si desea empaquetar la aplicación o el archivo Jar de tiempo deejecución.

Si elige Aplicación, puede seleccionar uno de los formatos siguientes:

404 Programación con VisualAge RPG

Page 423: c 0924494

v Archivos de aplicación

Incluye todos los archivos en el directorio de tiempo de ejecución y loscoloca en el directorio destino.

v Archivo Jar

Incluye todos los archivos para un componente en su propio archivo Jar.(Cualquier archivo de imagen GIF se copiará y no se incluirá en elarchivo Jar.)

v Incluir JDBC

Incluir el archivo de funciones de la clase JDBC en el jar.

Cómo empaquetar el archivo Jar de aplicaciónSi selecciona que su aplicación se empaquete como archivo Jar, aparece la siguienteventana:

Especifique el directorio destino. También puede especificar opciones Jar. Siselecciona Incluir archivo HTML, la página HTML por omisión para la aplicaciónse copiará en el directorio de destino. Si selecciona Exportar a AS/400, sevisualizará la Smart Guide para exportar archivos al sistema AS/400.

Nota: Si su aplicación tiene componentes múltiples, cada componente dispondráde su archivo Jar. Asimismo, cualquier archivo de imagen GIF sólo secopiará y no será incluido en el archivo Jar.

Capítulo 26. Cómo empaquetar el código de tiempo de ejecución y las aplicaciones 405

Page 424: c 0924494

Cómo empaquetar el tiempo de ejecuciónSi selecciona un archivo Jar de tiempo de ejecución, aparece la siguiente ventana:

Especifique el nombre del archivo Jar y el directorio de destino. Si seleccionaExportar a AS/400, se visualizará la Smart Guide para exportar archivos al sistemaAS/400.

406 Programación con VisualAge RPG

Page 425: c 0924494

Capítulo 27. Instalación del código de tiempo de ejecución ylas aplicaciones para Windows NT/95/98

En esta sección se describe la instalación del código de tiempo de ejecución y deaplicaciones para Windows NT/95/98, mediante InstallShield.

Nota: El código de tiempo de ejecución siempre debe instalarse antes de instalaruna aplicación. Sólo se instala una sola copia del código de tiempo deejecución en una estación de trabajo, sin importar cuántas aplicaciones seinstalen en la misma.

Instalación del código de tiempo de ejecuciónInicie el programa de utilidad de instalación mediante el mandatosetup.exe

del paquete y siga los pasos indicados en los recuadros de diálogo.

Los programas de utilidad Definir conexión a servidores, Definir información deAS/400 y Definir lista de servidores TCP/IP se instalan con el código de tiempo deejecución. Utilice estos programas de utilidad para mantener y actualizar losnombres y la ubicación de los recursos de AS/400 en el código de tiempo deejecución. Consulte el “Capítulo 8. Conectividad con AS/400” en la página 189 paraobtener más información.

Nota acerca del SQL incorporadoSi la aplicación tiene el SQL incorporado y hace referencia a una base de datos conla que la aplicación no se enlazó durante el tiempo de construcción, tiene quevolver a enlazar la aplicación con una base de datos a la que tenga acceso.

Instalación de una aplicaciónInstale la aplicación llamando al mandatosetup.exe

del paquete y siga los pasos indicados en los recuadros de diálogo.

El programa de utilidad Definir información de AS/400 se puede instalaropcionalmente con la aplicación. Utilice este programa de utilidad para mantener yactualizar los nombres y la ubicación de los recursos de AS/400 en el código detiempo de ejecución. Consulte el “Capítulo 8. Conectividad con AS/400” en lapágina 189 para obtener más información.

Mantenimiento del código de tiempo de ejecución y las aplicacionesPara actualizar el código de tiempo de ejecución o de aplicación, utilice el mismoprograma de instalación.

Para eliminar el código de tiempo de ejecución o las aplicaciones VisualAge RPG,realice las acciones siguientes:

© Copyright IBM Corp. 1994, 2000 407

Page 426: c 0924494

1. En el menú emergente Inicio de Windows NT/95/98 en la Barra de tareas,seleccione Configuración y Panel de control.

2. Invoque el programa de utilidad Agregar/quitar programas.

Instalación desde la LANEsta sección contiene información sobre las aplicaciones Windows que se ejecutanen Windows NT/95/98.

Para ejecutar desde la LAN:1. Empaquete el código de tiempo de ejecución o las aplicaciones en un servidor

LAN.2. Instale el código de tiempo de ejecución o las aplicaciones en el directorio raíz

del mismo servidor. El nombre del directorio debería ser VRPGRT_LAN para elcódigo de tiempo de ejecución o XXX_LAN para la aplicación. XXX es elnombre del archivo ejecutable de la aplicación.

3. Instale el código de tiempo de ejecución en la estación de trabajo clientemediante el paquete del paso 1. Seleccione la opción compactada.

4. Instale la aplicación mediante el paquete del paso 1. Seleccione la opcióncompacta.

Instalación silenciosa desde la LANEn esta sección se describe cómo instalar el código de tiempo de ejecución o lasaplicaciones de manera silenciosa desde un servidor LAN. Los pasos básicos sonlos siguientes:1. Empaquete el código de tiempo de ejecución o aplicación en el servidor LAN

utilizando el programa de utilidad de empaquetamiento. (Consulte el tema“Cómo empaquetar el código de tiempo de ejecución y las aplicaciones deVisualAge RPG” en la página 399 para obtener instrucciones).

2. Instale el tiempo de ejecución o la aplicación en el servidor LAN mediante laopción -r del programa de instalación:setup -r

El parámetro r permite que el sistema grabe las pulsaciones de teclasefectuadas durante el proceso de instalación. Esta información se almacena enel archivo setup.iss que se crea en el directorio de Windows. Estas pulsacionesde teclas se utilizarán en la instalación silenciosa.

3. Copie el archivo setup.iss del directorio de Windows al directorio LAN en elque ha empaquetado el tiempo de ejecución o la aplicación. Por ejemplo, sic:\winnt es el directorio de Windows, el archivo setup.iss se encontrará bajoc:\winnt.

Nota: Asegúrese de copiar el archivo setup.iss del tiempo de ejecución antes deinstalar la aplicación en el directorio LAN con la opción r. De locontrario, el archivo setup.iss de la instalación de la aplicación se grabaráencima del archivo setup.iss que ha creado la instalación del tiempo deejecución.

4. Modifique la copia del archivo setup.iss situado en el directorio LAN en el queha empaquetado el tiempo de ejecución o la aplicación. Cambie la entradaszDir de modo que apunte a la unidad y el directorio de destino en el quedebe instalarse el paquete del tiempo de ejecución o aplicación.

5. En la estación de trabajo cliente, diríjase al directorio LAN en el que se haempaquetado el tiempo de ejecución o la aplicación. Ejecute el siguientemandato:

408 Programación con VisualAge RPG

Page 427: c 0924494

setup -s

Tras instalar el tiempo de ejecución, concluya el sistema operativo yrearránquelo.

Capítulo 27. Instalación del código de tiempo de ejecución y las aplicaciones para Windows NT/95/98 409

Page 428: c 0924494

410 Programación con VisualAge RPG

Page 429: c 0924494

Parte 6. Apéndices

© Copyright IBM Corp. 1994, 2000 411

Page 430: c 0924494

412 Programación con VisualAge RPG

Page 431: c 0924494

Apéndice A. Archivos de aplicación

Esta sección describe todos los archivos que VisualAge RPG produce cuando secrea una GUI, se escribe una lógica o se construye una aplicación. A menos que sehaya especificado, no edite, renombre o elimine estos archivos del directorio enque se crearon.

Nota: Para aplicaciones Java, es RT_JAVA. Para aplicaciones de WindowsNT/95/98, es RT_WIN32.

Tabla 22. Archivos de aplicación

Nombre de archivo Formato Descripción

nombrearchivo.CLASS Binario El directorio de tiempo de ejecucióncontiene el archivo nombrearchivo.CLASS,que se crea cuando se compila un proyectopara Java.

nombrearchivo.DLL Binario El directorio de tiempo de ejecucióncontiene el archivo nombrearchivo.DLL, quese crea mediante el archivo .VPG. Una DLLVisualAge RPG es el objeto programa parala aplicación. El compilador también puedecrear una DLL del programa de utilidad ysu archivo .LIB correspondiente.

nombrearchivo.EVT ASCII El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.EVT, quecontiene errores de retorno del compilador.

nombrearchivo.EXE Binario El directorio de tiempo de ejecucióncontiene el archivo nombrearchivo.EXE, quecontiene la línea principal del tiempo deejecución. El compilador también puedecrear un EXE que contenga el archivo deejecución.

nombrearchivo.HLP Binario El directorio de tiempo de ejecucióncontiene el archivo nombrearchivo.HLP, quees el archivo de ayuda compilado que secreó utilizando los archivos .IPF, .IPM, .VPGy .TXM.

nombrearchivo.HTM ASCII El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.HTM,que incluye código HTML para la ejecucióndel programa Java compilado como unaapplet.

nombrearchivo_applet.HTM ASCII El directorio fuente de la aplicacióncontiene el archivonombrearchivo_applet.HTM, que incluyecódigo HTML que verifica el tiempo deejecución de Java en VARPG paraasegurarse de que el usuario tiene laversión correcta instalada como extensión.

nombrearchivo.IPF ASCII El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.IPF, quecontiene toda la información de controlnecesaria para crear ayuda en línea.

© Copyright IBM Corp. 1994, 2000 413

Page 432: c 0924494

Tabla 22. Archivos de aplicación (continuación)

Nombre de archivo Formato Descripción

nombrearchivo.IPM ASCII El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.IPM, quecontiene toda la ayuda de segundo nivelescrita para los mensajes de las ventanas ysus componentes.v No renombre o elimine este archivo del

directorio en el que se creó.v Utilice el Diseñador GUI (ventana Definir

mensajes) para editar este archivo. Sidebe editar este archivo fuera delDiseñador GUI, limite las modificacionesa la simple edición de texto, como lacorrección de errores gramaticales y deortografía. No elimine ni modifique losID de recurso, ni añada o suprimamensajes.

nombrearchivo.JAVA ASCII El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.JAVA,que contiene la fuente Java generada comoresultado de una compilación de Java.

nombrearchivo.LIB Binario El archivo nombrearchivo.LIB contienetodos los procedimientos exportados queforman parte de un nombrearchivo.DLL delprograma de utilidad.

nombrearchivo.LST ASCII El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.LST, quecontiene el listado de compilación.

nombrearchivo.ODF Binario oASCII

El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.ODF, quecontiene toda la información sobre lasventanas de la aplicación y suscomponentes.v No renombre o elimine este archivo del

directorio en el que se creó.v Este archivo sólo puede editarse

mediante el Diseñador GUI.

nombrearchivo.ODX ASCII El directorio fuente contiene el archivonombrearchivo.ODX, que se crea mediantenombrearchivo.ODF y se utiliza en tiempode ejecución.

nombarchRecursos.propiedades ASCII El directorio de tiempo de ejecucióncontiene el archivonombrearchivoRecursos.propiedades, quecontiene todos los mensajes escritos para lasventanas y sus componentes, en formatoJava.

414 Programación con VisualAge RPG

Page 433: c 0924494

Tabla 22. Archivos de aplicación (continuación)

Nombre de archivo Formato Descripción

nombrearchivo.RST ASCII El directorio fuente contiene la copiamaestra de este archivo. nombrearchivo.RSTcontiene todos los pseudónimos deservidores, alteraciones temporales dearchivos, alteraciones temporales de áreasde datos, alteraciones temporales deprogramas y la información de nivel debloqueo definida para la aplicación. Puedecambiar el contenido de este archivo entiempo de construcción utilizando elDiseñador GUI, o utilizando el programa deutilidad Definir información de AS/400 entiempo de ejecución.

nombrearchivo.TXC ASCII El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.TXC, quecontiene todas las notas de programaciónguardadas en los campos de edición devarias líneas proporcionados paraalmacenar descripciones técnicas.v No renombre o elimine este archivo del

directorio en el que se creó.v Para cambiar los valores de un

componente utilice un cuaderno devalores.

nombrearchivo.TXM ASCII El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.TXM,que contiene todos los mensajes escritospara las ventanas y sus componentes.v No renombre o elimine este archivo del

directorio en el que se creó.v Utilice el Diseñador GUI (ventana Definir

mensajes) para editar este archivo. Sidebe editar este archivo fuera delDiseñador GUI, limite las modificacionesa la simple edición de texto, como lacorrección de errores gramaticales y deortografía. No elimine ni modifique losID de recurso (idrec), ni añada o suprimamensajes.

nombrearchivo.VCX Binario Los directorios de tiempo de ejecución y defuente de la aplicación contienen el archivonombrearchivo.VCX, que contieneinformación de permanencia para cualquiercomponente ActiveX utilizado en suaplicación.

nombrearchivo.VPF ASCII El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.VPF, quecontiene todo el texto de ayuda escrito paralas ventanas y sus componentes.v No renombre o elimine este archivo del

directorio en el que se creó.v Puede editar este archivo utilizando el

editor del Diseñador GUI (mediante unmenú emergente para un componente omediante un cuaderno de propiedades).

Apéndice A. Archivos de aplicación 415

Page 434: c 0924494

Tabla 22. Archivos de aplicación (continuación)

Nombre de archivo Formato Descripción

nombrearchivo.VPG ASCII El directorio fuente de la aplicacióncontiene el archivo nombrearchivo.VPG,que contiene todo el código fuente escritode la aplicación VisualAge RPG.v No renombre o elimine este archivo del

directorio en el que se creó.v Utilice el Diseñador GUI para editar el

código fuente.

416 Programación con VisualAge RPG

Page 435: c 0924494

Apéndice B. Cómo escribir aplicaciones de cliente ligero

Las aplicaciones VisualAge RPG que fundamentalmente se ejecutan y utilizan losrecursos de las estaciones de trabajo se denominan aplicaciones de cliente grueso.Las aplicaciones de cliente ligero esencialmente confían al servidor AS/400 larealización de sus procesos y limitan al cliente al tratamiento de la GUI.

Las aplicaciones de cliente grueso siguen el estilo de programación que puedeencontrarse en las aplicaciones actuales de RPG III o RPG IV, pero esencialmente seejecutan en la estación de trabajo en lugar de en el servidor AS/400. Lasespecificaciones de archivo se utilizan para especificar que base de datos debeaccederse y las operaciones de RPG nativo como READ, CHAIN y otras, seutilizan para acceder a los datos del servidor. El sistema AS/400 funciona comoservidor de datos y realiza cálculos mínimos para dar soporte a la aplicaciónVARPG.

El modelo de cliente grueso tiene varias desventajas si lo comparamos con elcliente ligero. Su capacidad de reutilización de módulos es muy limitada y seproduce un incremento en el coste de la actividad general asociada a la gestión decambios. De igual manera, el traslado del proceso a la estación de trabajo clienteutiliza la energía de proceso del servidor.

El aligeramiento de la porción cliente de una aplicación ofrece las ventajassiguientes:v Se puede reducir fácilmente la cantidad de código que se ejecuta en el cliente.v Se mejora la capacidad de reutilización de la aplicación.v Se facilita el mantenimiento de código complejo.

Esta sección habla sobre dos implementaciones posibles del modelo de clienteligero. Ambas implementaciones aprovecha diversas capacidades de VARPG queproporcionan integración con el servidor AS/400. Ambos ejemplos incluyencapacidades que utilizan:v Descripción externa de las estructuras de datos para definir con facilidad datos

descritos externamente en una estructura de datos sin necesidad de utilizar elacceso directo a archivos.

v Interfaz de llamada remota para proporcionar una forma sencilla de invocarprogramas de servidor y enviar datos.

v Campos de referencia del Diseñador GUI. Los campos del subarchivo de lainterfaz de usuario se definen como campos de referencia, no se necesita unadefinición adicional de los campos de la base de datos.

Cómo implementar el modelo de aplicación VARPG ligeraEl modelo de aplicación VARPG ligera puede implementarse de varias formasdistintas. Describiremos dos de ellas. Una implementación utiliza llamadas remotasa un sistema AS/400; la otra utiliza colas de datos en el sistema AS/400. En amboscasos se utiliza la misma interfaz de usuario.

La aplicación de cliente simple lee datos de un archivo de un cliente y rellena unsubarchivo con 10 registros cada vez. La siguiente ilustración muestra la interfazde usuario de esta aplicación:

© Copyright IBM Corp. 1994, 2000 417

Page 436: c 0924494

La interfaz consiste en una ventana con lienzo, un subarchivo y un pulsador paracargar una página de registros Más en el subarchivo. El tamaño del subarchivopara este ejemplo concreto es de 10 registros. Puede cambiarse incrementando laaltura del componente subarchivo.

En el ejemplo se utilizan los siguientes nombres:

ComponenteNombre

VentanaWIN1

SubarchivoSUB1

PulsadorPSBMORE

Aplicación de ejemplo que utiliza llamadas remotasEn los programas RPG AS/400 tradicionales, el código de la interfaz y la lógica deacceso a la base de datos están mezclados en un módulo. Parte de esta estructurase origina en la historia de RPG y otra parte en el uso del OPM (Original ProgramModel) que obliga al programador a conseguir un alto rendimiento. Una forma deimplementar el modelo de aplicación ligera es subdividir completamente la lógicade la interfaz de usuario de la lógica de acceso a la base de datos y hacer que cadaparte se ejecute en diferentes sistemas. La lógica de la interfaz de usuario se ejecutaen un cliente Windows, la lógica de acceso a la base de datos se ejecuta en elservidor AS/400.

Esta aplicación de ejemplo muestra cómo dar soporte a la lectura de registros dedatos de la base de datos AS/400 y cómo poner esos datos en un subarchivo GUI.El programa que está en el servidor AS/400 puede también dar soporte a un

Figura 109. Interfaz GUI de cliente

418 Programación con VisualAge RPG

Page 437: c 0924494

acceso completo a la base de datos (READ y WRITE). Esto podría implementarseproporcionando un programa por cada para cada método de acceso diferente opasando las operaciones deseadas como parámetros a un único programa servidor.

El siguiente diagrama muestra cómo funciona este ejemplo:

El programa cliente recibe peticiones desde la interfaz de usuario. Invoca unprograma servidor que lee los registros de un programa de la base de datos y pasaesos datos de nuevo al cliente mediante parámetros. El subarchivo se va llenandocon los datos devueltos.

El programa clienteEl principal componente del componente cliente del programa es la interfaz deusuario. Se crea de la misma forma que cualquier aplicación VARPG y puedeutilizar las descripciones externas de base de datos del AS/400 mediante el uso decampos de referencia a base de datos. Cualquier comprobación de la validaciónespecificada en la base de datos la realiza el tiempo de ejecución de VARPGautomáticamente en el cliente. El programa cliente solicita datos del servidorinvocando un programa de acceso a datos del servidor; los datos en sí se pasan através de parámetros. El programa cliente no utiliza especificaciones de archivo; ensu lugar, la definición de los datos se realiza mediante estructuras de datosdescritas externamente. De esta forma el programador sigue disponiendo de lasventajas de las descripciones externas de campo en los programas VARPG.

Fuente RPG de ejemplo para el componente clienteEl programa VARPG consiste en especificaciones D y C. Las especificaciones Dcontienen las siguientes definiciones de datos:v Los campos utilizados como parámetros:

– cust, una estructura de aparición múltiple– custelem, un campo numérico, que contiene el número máximo de registros

que se están solicitando– eof, un indicador nombrado, que se pasa cuando el indicador de fin de

archivo se establece en ON en el programa servidor– nrecords, un campo numérico, que contiene el número de registros devueltos

v Dos campos de trabajo:– fileend, un indicador de nombre, para mantener la condición de fin de archivo– counter, un contador para el bucle DO

Interfaz de llamada entre cliente y servidor

Cliente

Rellenar subarchivo

AS/400

Programacliente

Estructurade datos

Subarchivo

Programaservidor

Archivo debase de datos

El cliente llama alprograma servidor- accede a la base de datos- finaliza con RETURN- pasa los datos de la DScomo parámetro

Apéndice B. Cómo escribir aplicaciones de cliente ligero 419

Page 438: c 0924494

v getrec, una constante, que define el programa al que llama el servidor. Define elenlace con el servidor y el nombre del programa servidor. El nombre delprograma debe especificarse en mayúsculas.

HD cust e ds extname(customer)D occurs(10)D inzD eof s n inzD nrecords s 2 0D fileend s n inzD getrec c linkage(*server)D const('GETREC')D counter s 2 0D custelem s 2 0 inz(%elem(cust))

Las especificaciones C contienen una subrutina de acción que tiene un enlace con 3eventos:v El evento Press del pulsador PSBMorev El evento Create de la ventana Win1 (Con un enlace con la subrutina de acción

PSBmore/press)v El evento Pageend del subarchivo Subf1

La primera sentencia es una llamada al programa servidor para que proporcionemás registros. El resto de la lógica se limita a procesar los datos pasados medianteparámetros y los traslada al subarchivo desde la estructura de datos de apariciónmúltiple. Una vez que el subarchivo se ha llenado con un conjunto de registros elnúmero más alto de registros del subarchivo se aplica al atributo SETTOP paratrasladar este conjunto de registros al área visible del subarchivo.

Al final, si se alcanza el fin de archivo, el pulsador Más se inhabilita. Observe quelas teclas Av Pág todavía funcionan. Es todavía posible provocar un evento quedesencadene esta subrutina de acción incluso con un pulsador inhabilitado.*

C PSBmore begact PRESS win1C call GETRECC parm custC parm custelemC parm eofC parm nrecordsC eval counter=1C dow counter<=nrecords and not fileendC counter occur custC write sub1C eval counter=counter+1C enddoC eval %setatr('win1':C 'sub1':'settop')=%getatr('win1'§C 'sub1':'count')

C if eofC eval %setatr('win1':C 'psbmore':'enabled')=0C eval fileend=*onC endif*

C endact

Como puede ver, la parte de código que corresponde al cliente es sencilla yminimiza el proceso en la estación de trabajo.

420 Programación con VisualAge RPG

Page 439: c 0924494

El programa servidorDebido a que el programa cliente VARPG no incluye la lógica de acceso a la basede datos, el programa servidor será quien proporcione ahora esta función. Elprograma servidor contiene todas las definiciones y operaciones FILE con las quetrata el proceso de la base de datos. Los datos se intercambian trasladando unaestructura de datos como parámetro entre los programas cliente y servidor. Laestructura de datos contiene las definiciones de campo del formato de registro delarchivo de datos. En este ejemplo, una estructura de datos de aparición múltiple seutiliza para acceder a una colección de registros. El número de apariciones es elmismo que el número de registros que deben pasarse; en este ejemplo, 10.Cualquier información de tipo operativo, como por ejemplo la información deerrores, puede también pasarse como parámetro. La llamada del programa clienteVARPG invoca al programa servidor, que finaliza tras cada llamada. El código dela operación Return se utiliza para finalizar el programa y mantener el entorno dellamada. Esto supondrá ventajas en el rendimiento para las llamadas posteriores, alno precisar de inicialización. Asimismo, precisa que se haya creado el programapara ejecutarse en un grupo de activación nombrado, ya que *NEW destruiríainmediatamente el entorno de llamada y el espacio disponible.

Fuente RPG de ejemplo para el componente servidorLa especificación de archivo define el archivo de base de datos externo Customer.Las especificaciones de definición de datos definen los parámetros a pasar. Estosdeben definirse de la misma forma que en el componente cliente. La cuenta deregistros representa una variable de trabajo para el contador del bucle DO.Custelem contiene el número de elementos de la estructura de datos CUST y seutiliza como límite para el bucle DO.* Programa para leer un conjunto de registros en una estructura de datos**********************************************************

Fcustomer if e diskD cust e ds extname(customer)D occurs(20)D eof s nD count s 2 0D custelem s 2 0

Al principio de las especificaciones de cálculo, el código de operación PLIST definelos parámetros que se pasan a este programa. El bucle DO lee del archivo de basede datos y pone los datos en la estructura de datos CUST, que a su vez volverá apasarse al programa cliente como un parámetro. Los otros dos parámetros sóloindican el estado del acceso a la base de datos:v EOF se establecerá en ON si la sentencia READ establece el indicador 99.v La cuenta de registros contiene el número de registros que vuelven a pasarse al

cliente en la estructura de datos CUST.C *entry plistC parm custC parm custelemC parm eofC parm countC eval count=1C count occur custC read customer 9999C dow count<custelem and not *in99C eval count=count+1C count occur custC read customer 9999C enddoC if *IN99

Apéndice B. Cómo escribir aplicaciones de cliente ligero 421

Page 440: c 0924494

C eval count=count-1C eval eof=*onC endifC return

Al compilar el programa servidor, asegúrese de no especificar *NEW para el grupode activación. Si se especifica *NEW (el valor por omisión), todo elalmacenamiento asignado por este programa se liberará al ejecutar RETURN. Unade las ventajas de este ejemplo de cliente ligero es la reutilización de la aplicaciónde servidor por distintas aplicaciones. Incluso las aplicaciones 5250 tradicionalespueden utilizar módulos de servidor para acceder a bases de datos. De esta formase facilita el mantenimiento de aplicaciones ya que los cambios en un módulo deservidor se reflejan en todas las aplicaciones que lo utilizan.

Aplicaciones de ejemplo que utilizan colas de datosEl sistema AS/400 proporciona soporte de colas de datos incorporado parapermitir la comunicación asíncrona entre aplicaciones. Esta aplicación de ejemploaprovecha las colas de datos, en lugar de pasar parámetros, para intercambiar losdatos de la base de datos con el programa cliente VARPG. Esta aplicación estábasada en dos colas de datos del servidor utilizadas por los programas cliente yservidor. El programa servidor de este ejemplo se inicia como un programaindependiente en el servidor utilizando la palabra clave NOWAIT en lasespecificaciones D del programa cliente.

Los diagramas siguientes ilustran cómo funciona este ejemplo.

Primero, se crean dos colas de datos y se inicia el programa servidor DATAQ. Elprograma servidor empieza a solicitar datos de la cola de datos ’O’ y permaneceen espera indefinida.

El siguiente estado se especifica cuando un evento GUI solicita más datos.(Consulte la Figura 109 en la página 418 para la interfaz de cliente.) Los treseventos que desencadenan la subrutina de acción son:v Evento Create de la ventanav Evento Press del pulsador Más...v Evento Pageend del subarchivo

El programa cliente entonces espera datos de la cola de datos ’I’. El programaservidor accede al archivo de base de datos y obtiene los datos.

El programa servidor est á a la espera de peticiones

Cliente

AS/400

En esperade peticiones

Programacliente

Cola de datos O Cola de datos I

Programaservidor

Subarchivo

422 Programación con VisualAge RPG

Page 441: c 0924494

En el tercer estado, el programa servidor llena la cola de datos ’I’. El programacliente se activa y transfiere los datos al subarchivo. Después, el programa regresaa su estado inicial y el proceso vuelve a empezar.

La aplicación de clienteLa interfaz de usuario es la misma que la de la anterior aplicación, esencialmenteun subarchivo que se llena con datos de una base de datos del servidor AS/400. Elsubarchivo empieza a llenarse con el evento Create de la ventana, y continúacuando se presiona el pulsador Más... o se produce un evento Pageend utilizandolas teclas de avance de página. Esencialmente, se trata de lo mismo que en elanterior ejemplo.

La configuración de las colas de datos se realiza en la subrutina de inicialización*INZSR, que invoca un programa en el servidor para crear dos colas de datos enuna biblioteca del sistema AS/400. Para crear colas de datos exclusivas para cadacliente, los cinco últimos caracteres de la dirección IP se codifican en el nombre dela cola de datos. Los caracteres ’I’ u ’O’ al final del nombre de una cola de datosproporcionan los nombres exclusivos para las colas de datos de entrada o desalida.

El trabajo del servidor recibe mandatos de la cola de datos ’O’; los mandatos seenvían a la cola de datos ’O’ desde el programa cliente.

El programa cliente solicita datos

Cliente

AS/400

Programacliente

Cola de datos O

Programaservidor

Cola de datos I

En espera de datos

Recibiendodatos

Enviando petición

Recibiendopeticiones

El programa servidor env ía datos

Cliente

AS/400

Enviando datos

Programacliente Subarchivo

Cola de datos O

Programaservidor

Cola de datos I

rellenandosubarchivocon datos

Recibiendodatos

Recibiendo datos

Apéndice B. Cómo escribir aplicaciones de cliente ligero 423

Page 442: c 0924494

Una vez creadas las colas de datos, el programa cliente invoca el programaservidor y le pasa los dos nombres de colas de datos. El programa servidor esperaque la cola de datos ’O’ le envíe mandatos del programa cliente.

El programa cliente se activa mediante eventos GUI y entonces envía peticiones ala cola de datos ’O’. Entonces espera a que la cola de datos ’I’ se llene de datosprocedentes del trabajo del servidor.

Cuando el programa cliente recibe una petición de finalización, se invoca lasubrutina *TERMSR para indicar al programa servidor que debe terminar y seeliminarán las dos colas de datos.

Fuente de ejemplo para el clienteEste programa es algo más extenso debido a que el entorno de cola de datostambién debe gestionarse en él.

Definiciones de datos

Las definiciones de datos para el programa cliente:v El archivo DLL getHostName es un archivo DLL de Windows que se utiliza para

obtener la dirección IP del cliente con la que crear nombres exclusivos para lascolas de datos.

D* Prototipo para archivos DLLD* Este archivo dll obtiene la dirección IP de la estación de trabajo,D* así como el nombre de sistema principal de WINDOWS TCPIPD* Este es el prototipo para invocar este archivo DLLD gethostname pr extproc('getHostName')D DLL('HOSTNAME.DLL')D Linkage(*STDCALL)D 10aD 15aD enthname s 10aD entipadd s 15aD* Series del mandato para crear y eliminar las colas de datosD QCMDEXC s 10 inz('QCMDEXC')D linkage(*server)D cmd s 256 INZD cmdlen s 15p 5 inz(%size(cmd))D cmd1 s 256 INZ('CRTDTAQ DTAQ(CWDATAQ/')D cmde s 256 INZ('DLTDTAQ DTAQ(CWDATAQ/')D cmd2 s 9 inz(') MAXLEN(')D* prefijo para el nombre de DATAQD qname1 s 4 inz('CUSQ')D qname2 s 5D* variables que contienen los dos nombres de colas de datosD* utilizados por un clienteD qnamei s 10D qnameo s 10DD* definir los programas RCVDTAQ y SNDDTAQ como programas de servidorD QRCVDTAQ s 10 inz('QRCVDTAQ')D linkage(*server)D QSNDDTAQ s 10 inz('QSNDDTAQ')D linkage(*server)D* definición del programa servidor RPGIVD DATAQ s 10 inz('DATAQ')D linkage(*server) nowaitD* estructura de datos que contiene datos de la base de datosD CustDS e ds extname(customer) occurs(10)D inzD* estructura de datos que contiene información de procesoD rinfo dsD eof n

424 Programación con VisualAge RPG

Page 443: c 0924494

D nrecords 2 0D filler 20D* límite del bucleD custelem s 2 0 inz(%elem(CustDS))D* indicador de que se ha alcanzado el fin de archivoD fileend s nD* parámetros para las API de cola de datosD msg_sz s 5 0D Name_of_Q s 10D Name_of_Lb s 10D count s 2 0D maxlen s 10 0 inz(%size(custds:*all))D wait_time s 5 0

La subrutina de inicialización

Una vez se han creado las colas de datos RPG y la DATAQ del programa RPGservidor se ha iniciado, se invoca el programa mediante la palabra clave NOWAIT,con lo que el programa cliente no esperará a que acabe. Ambos programas estánfuncionando de forma enteramente asíncrona.C*C* Subrutina de inicialización empleada parar la configuraciónC* del entorno servidorC*C *inzsr begsrC* Obtener de la dirección IP con la que construir nombre exclusivosC* para las colas de datosC* entipadd contendrá una dirección IP completaC callp getHostName(enthname:entipadd)C* Nombre de construcción de las colas de datos 'I' y 'O'C* Agregar los 5 últimos caracteres de la dirección IP a 'I' u 'O'C eval qnameI= qname1 +C %subst(entipadd:%lenC (%trim(entipadd))-5:5) + 'I'C eval qnameO= qname1 +C %subst(entipadd:%lenC (%trim(entipadd))-5:C 5) + 'O'C eval cmd=%trim(%trimr(cmd1) +C qnamei + cmd2 +C %editc(%size(C CustDS:*all):'Z') + ')')C* Crear colas de datosC call QCMDEXC 98C parm cmdC parm cmdlenC eval cmd=*blankC eval cmd=%trim(%trimr(cmd1) +C qnameo + cmd2 +C %editc(%size(C CustDS:*all):'Z') + ')')C call QCMDEXC 98C parm cmdC parm cmdlenC* Invocar el programa servidor para que acceda a la base de datos del servidorC call DATAQ 98C parm qnameiC parm qnameoC* Completada la inicialización, ahora a procesar eventosC endsr

La subrutina de acción

Apéndice B. Cómo escribir aplicaciones de cliente ligero 425

Page 444: c 0924494

Se envía una petición a la cola de datos ’O’. Entonces el programa cliente esperauna respuesta de la DATAQ del programa servidor, en la cola de datos ’I’. Una vezrecibidos los datos, el subarchivo se llena en un bucle.

C*C* Se invoca la subrutina de acción desde:C* - Evento Press del pulsador PSBMOREC* - Evento Create de la ventanaC* - Evento Pageend del subarchivoC*C PSBmore begact PRESS win1C* Mientras haya datos, debe obtenerse más datosC if not fileendC*C* Enviar petición a la cola de datos 'O' para que obtenga más datosC*C eval nrecords=10C call QSNDDTAQC parm qnameoC parm 'CWDATAQ' NAME_OF_LB 10C parm 23 MSG_SZ 5 0C parm rinfoC* Esperar datos de la cola de datos 'I'C* Esperar datos de proceso en DS rinfoC eval wait_time=-1C eval MSG_sz=23C call QRCVDTAQC parm qnameiC parm 'CWDATAQ ' NAME_OF_LBC parm MSG_SZC parm rinfoC parm WAIT_TIMEC* Esperar los datos de la base de datosC eval Msg_sz=%size(custds:*all)C call QRCVDTAQC parm QNAMEIC parm 'CWDATAQ ' NAME_OF_LBC parm MSG_SZC parm CustDSC parm WAIT_TIMEC* Llenar el subarchivo con todos los registros que haya leído el servidorC eval count=1C dow count<=nrecords and not fileendC count occur CustDSC write sub1C eval count=count+1C enddoC* Si se ha indicado el fin de archivo, desactivar el pulsadorC if eofC eval %setatr('win1':C 'psbmore':'enabled')=0C eval fileend=*onC endifC endif* fin de la subrutina de acción

C endact

Interrumpir la subrutina

Se envía una petición de interrupción a la DATAQ del programa servidor y las doscolas de datos se eliminan.C* Cuando la app del cliente finaliza, limpiar el entorno de servidorC*C *termsr begsrC* Indicar fin de programa al programa servidor y enviar datos a la DATAQ 'O'

426 Programación con VisualAge RPG

Page 445: c 0924494

C eval nrecords=0C call QSNDDTAQ 98C parm qnameoC parm 'CWDATAQ' NAME_OF_LB 10C parm 23 MSG_SZ 5 0C parm rinfoC* Eliminar ambas colas de datosC eval cmd=*blankC eval cmd=%trim(%trimr(cmde) +C qnamei + ')')C call QCMDEXC 98C parm cmdC parm cmdlenC eval cmd=*blankC eval cmd=%trim(%trimr(cmde) +C qnameo + ')')C call QCMDEXC 98C parm cmdC parm cmdlenC* La aplicación concluyeC endsr

El programa servidorUna vez se ha iniciado, entra en un bucle y espera a la cola de datos ’O’ hasta querecibe una petición del programa cliente. En este ejemplo, son posibles dospeticiones diferentes. El programa determina qué petición se ha enviado: la deenviar más datos o la de finalizar.

Para una petición de más datos leerá 10 registros más de la base de datos yenviará dos ítems a la cola de datos ’I’.

El primer ítem contiene información de proceso; cuántos registros se leyeron y si seha producido una situación de fin de archivo.

El segundo ítem contiene la estructura de datos de aparición múltiple con los datosdel archivo de la base de datos.

El programa cliente recibirá estos registros de la cola de datos ’I’ y llenará elsubarchivo de acuerdo con ellos.

Cuando el programa servidor recibe la señal de que se solicita una interrupción, seactivará el indicador LR y finalizará el bucle DO. Esto finalizará el programa.Cualquier otra operación de limpieza será gestionada por el programa cliente.

Fuente de ejemplo para el servidorDefiniciones de archivo y de datosFcustomer if e diskD* estructura de datos que contiene datos de la base de datosD* que deben pasarse al clienteD CustDS e ds extname(customer) occurs(10)D* estructura de datos para pasar información de control entreD* cliente y servidorD rinfo dsD eof nD count 2 0D fill 20D* número de apariciones en DS para el límite del bucleD custelem s 2 0 inz(%elem(CustDS))D* nombre de la biblioteca para la DATAQ y el tamaño de los datos queD* deben enviarse a la DATAQ y al tiempo de esperaD Name_of_LB s 10 inz('CWDATAQ')

Apéndice B. Cómo escribir aplicaciones de cliente ligero 427

Page 446: c 0924494

D msg_sz S 5 0D wait_time s 5 0D* nombre de las DATAQ pasadas desde el clienteD qnamei s 10D qnameo s 10

Línea principal del programa

Procesar el bucle DO, esperar a la cola de datos ’O’ hasta que lleguen más datos dela base de datos, enviar los datos a la cola de datos ’I’ y seguir esperando máspeticiones.C* Principio de la línea principalC *entry plistC parm qnameiC parm qnameoC* El bucle DO se ejecuta constantemente hasta que el programa clienteC* le indica que se interrumpaC dow not *inlrC* Esperar a que el programa cliente indique que necesita datosC eval wait_time=-1C eval MSG_sz=23C call 'QRCVDTAQ'C parm qnameoC parm NAME_OF_LBC parm MSG_SZC parm rinfoC parm WAIT_TIMEC*C* Leer 10 registros del archivo de la base de datosC* cuenta de registros = 0 significa que el programa cliente se está interrumpiendoC if count >0C eval count=1C count occur CustDSC read customer 9999C dow count<custelem and not *in99C eval count=count+1C count occur CustDSC read customer 9999C enddoC* Determinar si hay más datos en el archivoC if *IN99C eval count=count-1C eval eof=*onC endif

C* Enviar información a la cola de datosC* Enviar un registro con información sobre cuántos registros se hanC* leído y si se ha alcanzado el fin de archivoC*C call 'QSNDDTAQ' 98C parm QnameIC parm NAME_OF_LBC parm 23 MSG_SZC parm rinfoC* Enviar los datos en DS desde el archivo de la base de datos a DATAQC eval msg_sz=%SIZE(custds:*all)C call 'QSNDDTAQ' 98C parm qnameiC parm NAME_OF_LBC parm MSG_SZC parm CUSTdsC* Cuando finaliza el programa cliente, envía nrecords 0, entonces esteC* programa acaba tambiénC elseC eval *inlr=*onC*

428 Programación con VisualAge RPG

Page 447: c 0924494

C endC enddoC*C* Fin de la línea principal

Otras implementaciones posiblesAdemás de estos ejemplos específicos, son posibles otras variaciones ycombinaciones de ambas implementaciones. El objetivo es minimizar los procesosdel cliente y utilizar la capacidad del servidor para que ejecute estas aplicaciones.La reutilización de los módulos del servidor puede conseguirse ya que lasaplicaciones 5250 y GUI pueden utilizar los mismos programas servidor.

Una implementación posible es el uso de peticiones en la forma de sentencias SQLque se pasan a un programa servidor. Este programa servidor emite la sentenciaSQL y direcciona los datos recibidos a una cola de datos. El programa cliente,esperando a la cola de datos, utiliza los datos que recibe para satisfacer la peticióndel usuario final. En esta aplicación particular, se utiliza una cola de datos de claveúnica en lugar de múltiples colas de datos.

Otra implementación podría pasar todos los datos de entrada desde la interfaz deusuario al programa servidor para realizar la comprobación de errores en elservidor; las condiciones de error se enviarían al cliente. Este método permite unalto grado de reutilización de la lógica del sistema entre las aplicaciones 5250 yGUI, a la vez que proporciona un cliente aún más ligero.

Ejemplo de programa servidor reutilizableEl código RPG IV siguiente para una aplicación de subarchivo 5250 utiliza elmismo programa servidor, pero en una interfaz 5250. Este ejemplo muestra lasposibilidades de reutilización de los programas servidor para aplicaciones GUI y5250. Los programas GUI de cliente ligero pueden utilizar fácilmente la lógica delsistema contenida en el programa servidor 5250. La siguiente ilustración muestraun ejemplo de la pantalla 5250 que muestra la misma información de base de datosque el ejemplo GUI al principio de este capítulo.

Apéndice B. Cómo escribir aplicaciones de cliente ligero 429

Page 448: c 0924494

Este subarchivo sólo tiene capacidad para 8 registros en pantalla debido a que cadaregistro ocupa dos filas del subarchivo. A continuación puede ver el fuente delprograma para esta aplicación:H* Programa para listar los registros del clienteF* Archivo Workstn que contiene DSPFFgetrecs cf e workstn sfile(sub1:recnum)D* estructura de datos para pasar datos del programa servidor al subarchivoDcust e ds extname(customer) occurs(8)D inzDeof s 1 inz(*off)Dnrecords s 2 0Dfileend s 1 inz(*off)Dcount s 2 0Dcustelem s 2 0 inz(%elem(cust))Drecnum s 5 0 inz(1)* Programa principal para invocar la subrutina del subarchivo y* finalizar el programa* In91 indica que el archivo de la base de datos no ha alcanzado el final

C EVAL *IN91=*ONC exsr moreC eval *inlr=*oncC more BEGsr* Bucle para obtener más datos y visualizarlos en un subarchivo

C dow not *in03* Invocar el programa servidor para que obtenga datos la primera vez* y cuándo se utiliza el avance de página

C if *in91C call 'GETREC'C parm custC parm custelemC parm eofC parm nrecordsC eval count=1* recnum1 es sbfrcdnbr en el registro de control del subarchivo,* para posicionar el primer registro que se visualizará en la pantalla

C EVAL RECNUM1=RECNUM* Bucle para llenar un subarchivo con nuevos registros

C dow count<=nrecords

430 Programación con VisualAge RPG

Page 449: c 0924494

C count occur custC write sub1C eval count=count+1C eval recnum=recnum+1C enddo* Una vez se ha añadido el conjunto de registros al subarchivo, visualizarlo,* además del formato del encabezamiento y del pie de página

C write record1C write footerC exfmt sub1ctl* Ignorar las teclas de Av Pág

C elseC read sub1ctl 99C endifC if eof=*on* IN90 habilita la tecla Av Pág para que puedan leerse más registros.* Al final del archivo se inhabilita.

C eval *in90=*onC eval recnum=recnum1C endifC enddo* Abandonar el bucle cuando se solicite Salir

C ENDSR

Apéndice B. Cómo escribir aplicaciones de cliente ligero 431

Page 450: c 0924494

432 Programación con VisualAge RPG

Page 451: c 0924494

Apéndice C. Creación y compilación de programas no GUIdesde MS-DOS

Puede crear aplicaciones VARPG autónomas en el diseñador de GUI de VARPG, obien emitiendo mandatos en una línea de mandatos de MS-DOS. Esta sección leproporciona los mandatos que puede utilizar en una línea de mandatos. Parautilizar el Diseñador GUI, consulte “Capítulo 21. Cómo crear programas no GUI enVisualAge RPG” en la página 357.

Para iniciar el editor y crear fuente en una línea de mandatos de MS-DOS, escriba:codeedit nombrearchivo.VPG

Asegúrese de incluir la extensión .VPG en el nombre del archivo para que puedabeneficiarse de las funciones de interpretación y comprobación de sintaxis queincorpora el editor.

Para ejecutar el compilador FVDFNFE, emita el mandato de compilador desde unalínea de mandatos de MS-DOS. La sintaxis del mandato es:fvdfnfe nombrearchivo.VPG [/compilador_opción1 ... /compilador_opciónn]

Nota: Debe incluir la extensión .VPG en el nombre del archivo fuente; no se dapor supuesta.

Las opciones del compilador, que puede escribir en mayúsculas o minúsculas, sonopcionales. Éstas son:

OpciónDescripción

/BL nombreNombre de la biblioteca de enlace. Si hubiera más de una, delimite losnombres mediante comillas.

/D Genera información de depuración

/GL 1-99Nivel de gravedad de generación

/L Genera un listado de salida

/LI Sangrado

/LX Genera un listado de referencias cruzadas (XREF)

/LV Genera un listado de referencias cruzadas visual (XREF)

/LD Expande DDS en listado

/LC Expande /COPY en listado

/LE Muestra referencias externas

/LM2 Muestra mensajes de segundo nivel en el listado

/LS Muestra las líneas excluidas en el listado

/LP 10-99Líneas por página (listado)

/HCU Habilita la antememoria en el sistema principal

© Copyright IBM Corp. 1994, 2000 433

Page 452: c 0924494

/HCR Renueva la antememoria en el sistema principal

/RF Corrije valores numéricos

/RN Permite valor nulo

/RNU Permite valor nulo bajo control del usuario

/RT Trunca valores numéricos

/TI Genera información de depuración (igual que /D)

/SB NombreNombre de archivo de enlace SQL

/SF XXFormato SQL para columnas de fecha y hora

/SI XX (RR RS CS UR) nivel de aislamiento de SQL

/SN NombreNombre de base de datos SQL

/SP NombreNombre de archivo de paquete SQL

/SR Bloqueo de registro de SQL

/SU ID de usuario de base de datos

/SUP Contraseña de base de datos

/SVC Carácter de variable de conversión

/SVG Gráfico de variable de conversión

Acceso a un sistema AS/400Si el programa debe acceder a datos ubicados en el sistema AS/400 o ejecutarprogramas AS/400, debe crear un archivo RST (Remote Server Table). El archivoRST es un archivo ASCII que lee el compilador y el tiempo de ejecución de VARPGpara determinar qué información sobre el sistema debe utilizar y la ubicación delos archivos. Un archivo RST se crea en el Diseñador GUI al utilizar el diálogoDefinir información de AS/400. Durante el tiempo de compilación, el archivo RSTdebe estar en el mismo directorio que el fuente del programa. Durante el tiempode ejecución, el archivo RST debe estar en el mismo directorio que los archivosejecutables del programa.

A continuación encontrará un ejemplo de un archivo RST:

DEFINE_SERVER SERVER_ALIAS_NAME(MYAS400)REMOTE_LOCATION_NAME(TORAS40Z)NETWORK_PROTOCOL(*TCP)TEXT(Development - RST)

DEFINE_FILE FILE_ALIAS_NAME(CUSTOMER)REMOTE_FILE_NAME(PRODUCT/CUSTMAST)SERVER_ALIAS_NAME(MYAS400)TEXT()

La sentencia DEFINE_FILE indica la ubicación de los archivos definidos en lasespecificaciones ’F’ en el sistema AS/400. En este ejemplo, el archivo CUSTOMERen la especificación ’F’ se refiere al archivo CUSTMAST en la biblioteca PRODUCT.

434 Programación con VisualAge RPG

Page 453: c 0924494

Si el archivo se encuentra en la lista de su biblioteca, puede omitir la sentenciaDEFINE_FILE. En tal caso, la búsqueda se llevará acabo en la lista de biblioteca*LIBL.

La palabra clave TEXT se utiliza para comentarios, por lo que puede estar enblanco.

Apéndice C. Creación y compilación de programas no GUI desde MS-DOS 435

Page 454: c 0924494

436 Programación con VisualAge RPG

Page 455: c 0924494

Glosario

Este glosario incluye términos y definiciones de:v El American National Dictionary for Information Systems ANSI X3.172-1990,

copyright 1990 del American National Standards Institute (ANSI). Si deseaadquirir una copia de esta publicación debe dirigirse al American NationalStandards Institute, 1430 Broadway, New York, New York, 10018. Lasdefiniciones se especifican mediante el símbolo (A) después de las mismas.

v El Information Technology Vocabulary desarrollado por el Subcomité 1, ComitéTécnico Conjunto 1, de International Organization for Standardization y elInternational Electrotechnical Committee (ISO/IEC JTC1/SC1). Las definicionesde las partes publicadas de este vocabulario se identifican mediante el símbolo(|) después de las mismas; las definiciones tomadas de borradores de estándaresinternacionales, borradores del comité y trabajos no concluyentes desarrolladospor ISO/IEC JTC1/SC1 se identifican mediante el símbolo (T) después de lasmismas, lo cual indica que aún no se ha alcanzado un acuerdo definitivo entrelos Organismos Nacionales integrantes del SC1.

v IBM Dictionary of Computing, New York: McGraw-Hill, 1994.v Object-Oriented Interface Design IBM Common User Interface Guidelines,

SC34-4399-00, Carmel, IN: Que Corporation, 1992.

Aacción. (1) Sinónimo de subrutina de acción. (2) Programa ejecutable o archivo de mandatos utilizado para manipularlos componentes de un proyecto o participar en una construcción.

acción por omisión. Acción que se efectúa cuando se realiza otra como, por ejemplo, pulsar la tecla Intro.

alias de servidor. Nombre al que da una definición y que puede utilizarse en lugar del nombre del servidor.

ancla. Cualquier componente que se utiliza como punto de referencia para alinear, dimensionar y espaciar otroscomponentes.

anotaciones de error. Realiza un seguimiento de los errores en las anotaciones de error. El editor le lleva al lugardel código fuente en el que se ha producido el error.

API. Interfaz de programación de aplicaciones.

aplicación. Un grupo de componentes de software utilizados para efectuar tareas de usuario específicas en unsistema.

applet. Programa escrito en Java que se ejecuta dentro de un navegador compatible con Java o AppletViewer.

archivo. Grupo de datos relacionados que se almacena y se recupera mediante un nombre asignado. Un archivopuede incluir información que inicia un programa (objeto de archivo de programa), contiene texto o gráficos (objetode archivo de datos) o procesa una serie de mandatos (archivo por lotes).

archivo de mensajes. Archivo que contiene mensajes de aplicación. Este archivo se crea a partir del archivo fuentede mensajes durante el proceso de construcción. Véase también construir.

archivo de ondas. Archivo utilizado para sonidos audio en un dispositivo de forma de onda.

archivo de Recurso de Presentación de Información (IPF). Archivo en el que se almacena el fuente de la ayuda dela aplicación.

archivo MIDI. Archivo de la Interfaz Digital de Instrumentos Musicales.

© Copyright IBM Corp. 1994, 2000 437

Page 456: c 0924494

archivos JAR (.jar). En Java, abreviatura de Java ARchive. Es un formato de archivo que se utiliza para agregarvarios archivos en uno.

área común. Área de almacenamiento proporcionada por el sistema para retener datos temporalmente. Los datos delárea común están disponibles para otras aplicaciones.

área de cliente. La parte de la ventana que es el espacio de trabajo del usuario donde éste teclea información yselecciona opciones de campos de selección. En ventanas primarias, el área en la que un programador de aplicacionespresenta los objetos con los que trabaja el usuario.

área de información. Componente de una ventana en el que se visualiza información sobre el objeto o la opción enlos que se encuentra el cursor. El área de información también puede incluir un mensaje sobre la conclusión normalde un proceso. Véase también barra de estado.

área de trabajo. Área utilizada para organizar objetos de acuerdo a las tareas del usuario. Cuando un usuario cierraun área de trabajo, todas las ventanas abiertas a partir de objetos contenidos en el área de trabajo se eliminan dellugar de trabajo.

Arquitectura Common User Access (arquitectura CUA). Directrices para el diálogo entre una persona y unaestación de trabajo o un terminal.

arquitectura CUA. Arquitectura de Acceso Común de Usuario.

arrastrar. Mover o copiar un objeto utilizando el ratón. Por ejemplo, un usuario puede arrastrar el borde de unaventana para hacerla más grande pulsando un botón del ratón y manteniéndolo pulsado mientras mueve el ratón.Véase también arrastrar y soltar.

arrastrar y soltar. Manipular directamente un objeto moviéndolo y colocándolo en cualquier lugar utilizando elratón.

ASCII (American National Standard Code for Information Interchange). Código estándar, que se compone de unjuego de caracteres codificados de 7 bits (8 bits incluyendo comprobación de paridad), que se utiliza para elintercambio de información entre sistemas de proceso de datos, sistemas de comunicación de datos y equipoasociado. El juego de caracteres ASCII se compone de caracteres de control y caracteres gráficos. (A)

atenuado. Atenuación del contraste visual de un componente que indica que el usuario no puede seleccionar nimanipular directamente ese componente.

Bbarra de desplazamiento. Componente que muestra a un usuario que hay más información disponible en unadirección determinada y que puede moverse para visualizar dicha información utilizando el ratón o las teclas depágina.

barra de estado. Componente de una ventana que visualiza información que indica el estado de la vista o del objetoactuales. Véase también área de información.

barra de herramientas. Menú que contiene una o más opciones gráficas que representa las acciones que un usuariopuede efectuar utilizando el ratón.

barra de títulos. Área en la parte superior de cada ventana que contiene el símbolo del menú del sistema.

base de datos. (1) Grupo de datos con una estructura determinada para aceptar, almacenar y proporcionar, previapetición, datos para varios usuarios. (T) (2) Todos los archivos de datos almacenados en el sistema.

Biblioteca de enlace dinámico (DLL). Archivo que contiene código ejecutable y datos enlazados de manera lógica aun programa durante el tiempo de carga o el de ejecución, en lugar de durante el enlace. Varias aplicaciones puedencompartir a la vez el código y los datos de una biblioteca de enlace dinámico.

BMP. Extensión de archivo de un archivo bitmap.

borde de dimensionamiento. Borde de un marco alrededor de un componente (o conjunto de componentes) queselecciona para cambiar el tamaño del componente (o del conjunto de componentes) utilizando el ratón o el teclado.

438 Programación con VisualAge RPG

Page 457: c 0924494

borde de selección. Borde visual que aparece alrededor de un componente de VARPG o de un componente creadopor el usuario, que permite moverlo con el ratón o el teclado.

botón. (1) Mecanismo en un dispositivo de puntero, como un ratón, utilizado para solicitar o iniciar una acción. (2)Mecanismo gráfico en una ventana que, cuando se selecciona, produce una acción. Por ejemplo, el pulsador Aceptarque, al seleccionarse, inicia una acción.

botón 1 del ratón. Por omisión, el botón izquierdo del ratón se utiliza para seleccionar.

botón 2 del ratón. Por omisión, el botón derecho del ratón se utiliza para manipular.

botón de manipulación. Véase botón 2 del ratón.

botón de maximizar. Botón en la parte más a la derecha de una barra de título sobre el que un usuario pulsa elbotón del ratón para aumentar el tamaño de la ventana lo máximo posible. Compárese con botón de minimizar y botónde ocultar.

botón de minimizar. Botón ubicado junto al botón más a la derecha en una barra de título que reduce el tamaño dela ventana lo máximo posible. Compárese con botón de maximizar y botón de ocultar.

botón de ocultar. Botón en una barra de título sobre el que un usuario pulsa el botón del ratón para suprimir unaventana del lugar de trabajo sin cerrarla. Cuando la ventana está oculta, el estado de la misma, indicado en la lista deventanas, cambia. Compárese con botón de maximizar y botón de minimizar.

botón de ratón. Mecanismo en un ratón para seleccionar opciones, iniciar acciones o manipular objetos con elpuntero. Véase también botón 1 del ratón y botón 2 del ratón.

botón de restaurar. Botón que aparece en la esquina más a la derecha de la barra de título después de habermaximizado una ventana. Cuando se selecciona el botón de restaurar, la ventana vuelve a tener el tamaño y laposición que tenía antes de que se maximizara. Véase también botón de maximizar.

botón de selección. Véase botón 1 del ratón.

Ccampo. (1) Área identificable en una ventana, como un campo de entrada, en la que un usuario escribe texto. (2)Grupo de bytes relacionados, como un nombre o una cantidad, que se trata como una unidad en un registro.

campo de referencia. Campo de la base de datos de AS/400 cuyas características un componente campo de entradapuede heredar.

campo de subarchivo. Campo utilizado para definir campos en un componente subarchivo. Véase también camposubarchivo.

Capa de Sockets Segura (SSL). Esquema de seguridad de gran aceptación desarrollado por NetscapeCommunications Corp. y RSA Data Security, Inc. SSL permite al cliente autenticarse en el servidor y cifrar todos losdatos y peticiones. El URL de un servidor seguro protegido mediante SSL empieza por https en lugar de http.

carpeta destino. Objeto en el que se coloca el icono que representa una aplicación VARPG.

catálogo de componentes. Espacio de almacenamiento para todos los componentes utilizados para crear interfacesgráficas de usuario para aplicaciones VARPG.

cliente. (1) Sistema que depende de un servidor para obtener datos. (2) La PWS donde se ejecutan las aplicacionesVARPG. Véase también cliente DDE.

cliente DDE. Aplicación que inicia una conversación DDE. Compárese con servidor DDE. Véase también componentecliente DDE y conversación DDE.

cliente/servidor. Modelo de interacción en el proceso de datos distribuidos en el que un programa en una ubicaciónenvía una petición a un programa en otra ubicación y espera una respuesta. El programa que efectúa la peticiónrecibe el nombre de cliente; y el programa que responde, servidor. Véase también cliente, servidor, cliente DDE, servidorDDE.

Glosario 439

Page 458: c 0924494

compilar. Convertir un programa fuente en un programa ejecutable (programa objeto).

componente barra de desplazamiento horizontal. Componente que añade una barra de desplazamiento horizontala una ventana. Este componente permite desplazarse por un panel de información de izquierda a derecha oviceversa.

componente barra de desplazamiento vertical. Componente que añade una barra de desplazamiento vertical a unaventana. Este componente permite desplazarse por un panel de información verticalmente.

componente barra de estado. Componente de una ventana que puede visualizar información adicional sobre unproceso o acción de la ventana.

componente barra de menús. Área que está junto a la parte superior de la ventana, debajo de la barra de título yencima del resto de la ventana, que contiene opciones que proporcionan acceso a otros menús. En VisualAge RPG, seseñala y pulsa un componente barra de menús de la paleta de componentes o del catálogo de componentes y sesuelta en una ventana de diseño.

componente barra de progreso. Componente que se puede utilizar para indicar el progreso de un proceso como,por ejemplo, copiar archivos, cargar una base de datos, etc. de forma gráfica.

componente bena Java. Componente que permite a las aplicaciones VARPG acceder a los JavaBean de SunMicrosystem.

componente botón de selección. Círculo con texto al lado. Los botones de selección se combinan para mostrar a unusuario un conjunto fijo de opciones de entre las que sólo puede seleccionarse una. Cuando se selecciona una opción,el círculo se rellena parcialmente. Puede señalar y pulsar un componente botón de selección de la paleta decomponentes o del catálogo de componentes y soltarlo en una ventana de diseño.

componente calendario. Componente que añade un calendario que puede ser modificado por el usuario para incluirtexto, color u otros atributos.

componente campo de entrada. Área de una pantalla donde un usuario pueden entrar información, a menos que elcampo sea de sólo lectura. Normalmente, los límites de un campo de entrada están indicados. En VisualAge RPG, seseñala y pulsa un componente campo de entrada de la paleta de componentes o del catálogo de componentes y sesuelta en una ventana de diseño.

componente cliente DDE. Componente utilizado para intercambiar datos con otras aplicaciones como, por ejemplo,aplicaciones de hoja de cálculo, que soportan el protocolo de intercambio de datos dinámico (DDE).

componente *component. Componente que es la “representación de componente” del componente lógico. Para cadacomponente lógico se crea un componente *component, que no se visualiza.

componente contenedor. Componente que almacena registros relacionados y los visualiza en una vista de detalles,de icono o de árbol.

componente control de animación. Componente que permite reproducir archivos de vídeo, con la extensión AVI, enWindows, o reproducir secuencias GIF de animación en aplicaciones Java.

componente cuaderno. Representación gráfica de un cuaderno. Puede añadir páginas de cuaderno al componentecuaderno y agrupar las páginas en secciones separadas por separadores. En Windows, a veces se hace referencia alcuaderno como el control de separadores de Windows. Véase también componente página de cuaderno y componentepágina de cuaderno con lienzo.

componente de activeX. Componente que añade objetos de control ActiveX al proyecto. Las aplicaciones VARPGpueden acceder así a los atributos y supervisar si hay eventos.

componente definido por el usuario. Componente, que se compone de uno o más componentes que hapersonalizado, que guarda en la paleta de componentes o del catálogo de componentes para volver a utilizarlo.Cuando está en la paleta o en el catálogo, este componente se puede señalar y pulsar en la ventana de diseño talcomo se haría con otro componente de VARPG.

componente destino. Componente que, siempre que cambia el estado del componente fuente, recibe un evento link(de enlace) del componente fuente.

440 Programación con VisualAge RPG

Page 459: c 0924494

componente de subarchivo. Componente utilizado para visualizar una lista de registros que constan de varioscampos. Este componente es similar a un subarchivo de AS/400. Véase también campo de subarchivo.

componente edición de múltiples líneas (MLE). Componente que representa un campo de entrada que permite alusuario entrar varias líneas de texto.

componente elemento de menú. Componente que es un elemento gráfico o de texto en un menú. Cuando elusuario desea trabajar con un objeto, selecciona un elemento de menú.

componente fuente. Componente que, siempre que cambia su estado, puede notificarlo a los componentes dedestino. Un componente fuente puede tener varios destinos.

componente graduador. Componente visual de una interfaz de usuario que representa una cantidad y su relacióncon el rango de posibles valores para esa cantidad. El usuario también puede modificar el valor de la cantidad.Puede señalar y pulsar un componente graduador de la paleta de componentes o del catálogo de componentes ysoltarlo en una ventana de diseño.

componente gráfica. Componente que permite al usuario añadir un gráfico a la GUI. Los estilos de gráficodisponibles son el diagrama de líneas, de barras, de líneas y barras y circular.

componente imagen. Componente utilizado para visualizar una imagen, de un archivo BMP o ICO, en una ventana.

componente lienzo. Componente en el que puede señalar y pulsar otros componentes, colocarlos y organizarlospara producir una interfaz gráfica de usuario. El componente lienzo ocupa el área de cliente de un componenteventana o de un componente página de cuaderno. Véase también componente página de cuaderno con lienzo ycomponente ventana con lienzo.

componente lógico. Agrupación funcional de archivos relacionados dentro de un proyecto. Se crea un componentelógica cuando las palabras clave NOMAIN y EXE no se encuentran en las especificaciones de control.

componente lógico compartido. Componente lógico al que puede accederse a través de más de un proyecto.

componente medios. Componente que proporciona a un programa la posibilidad de procesar archivos de sonido(.WAV) y archivos de vídeo (.MID).

componente menú emergente. Componente que, cuando se añade a un objeto en la interfaz, aparece junto al objetocon el que está asociado cuando se solicita. Puede señalar y pulsar un componente menú emergente de la paleta decomponentes o del catálogo de componentes y soltarlo en una ventana de diseño.

componente odbc/jdbc. Componente que permite a las aplicaciones VAPRG acceder y procesar archivos de base dedatos que den soporte a la API ODBC de Windows o la API JDBC de Sun Microsystem.

componente página de cuaderno. A part used to add pages to a notebook part. Véase también cuaderno.

componente página de cuaderno con lienzo. Combinación del componente cuaderno y del componente página conlienzo. Véase también cuaderno y componente lienzo.

componente panel de medios. Componente utilizado para proporcionar al usuario control sobre otros componentes.Por ejemplo, un componente panel de medios puede utilizarse para controlar el volumen de un componente medios.

componente pulsador. Botón etiquetado con texto que representa una acción que se inicia cuando un usuarioselecciona el pulsador. Puede señalar y pulsar un componente pulsador de la paleta de componentes o del catálogode componentes y soltarlo en una ventana de diseño. Véase también componente pulsador gráfico.

componente pulsador gráfico. Pulsador, etiquetado con un gráfico, que representa una acción que se inicia cuandoun usuario la selecciona. Compárese con componente pulsador.

componente recuadro de contorno. Componente que es un recuadro rectangular colocado alrededor de un grupo decomponentes para indicar que todos los componentes están relacionados.

componente recuadro de grupo. Marco rectangular alrededor de un grupo de controles que indica que estánrelacionados y que proporciona una etiqueta optativa para el grupo. En VisualAge RPG, se señala y pulsa uncomponente recuadro de grupo de la paleta de componentes o del catálogo de componentes y se suelta en unaventana de diseño.

Glosario 441

Page 460: c 0924494

componente recuadro de lista. Control que contiene opciones desplazables que un usuario puede seleccionar. EnVisualAge RPG, se señala y pulsa un componente recuadro de lista de la paleta de componentes o del catálogo decomponentes y se suelta en una ventana de diseño.

componente recuadro de selección. Recuadro de selección con texto asociado que representa una opción. Cuandoun usuario selecciona una opción, aparece un indicador en el recuadro de selección que indica que la opción estáseleccionada. El usuario puede eliminar la marca del recuadro de selección volviendo a seleccionar la opción. EnVisualAge RPG, se señala y pulsa un componente recuadro de selección de la paleta de componentes o del catálogode componentes y se suelta en una ventana de diseño.

componente referencia a componente lógico. Componente que permite que un componente lógico se comuniquecon otro en una aplicación VARPG.

componentes. Objetos que componen la GUI de una aplicación VARPG.

componente selector cíclico. Tipo de campo de entrada que muestra un anillo de opciones relacionadas, pero que seexcluyen mutuamente, por el que un usuario puede desplazarse y seleccionar una opción. El usuario también puedeteclear una opción válida en el campo de entrada. Puede señalar y pulsar un componente selector cíclico de la paletade componentes o del catálogo de componentes y soltarlo en una ventana de diseño.

componente subarchivo de mensajes. Componente que puede visualizar mensajes predefinidos o textosuministrado en la lógica del programa.

componente submenú. Componente utilizado para iniciar un submenú a partir de un elemento de menú o de unmenú existente, o para iniciar un menú desplegable a partir de un elemento de menú en una barra de menú. Véasetambién submenú y componente elemento de menú.

componente temporizador. Componente utilizado para hacer un seguimiento del intervalo de tiempo entre doseventos y activar el segundo evento cuando ha transcurrido el intervalo.

componente texto estático. Componente utilizado como etiqueta para otros componentes, como solicitud para uncomponente campo de entrada.

componente ventana. Área con límites visibles que representa una vista de un objeto o con la que un usuariomantiene un diálogo con un sistema. Puede señalar y pulsar un componente ventana de la paleta de componentes odel catálogo de componentes y soltarlo en la ventana de proyectos.

componente ventana con lienzo. Combinación del componente ventana y del componente lienzo. Véase tambiéncomponente ventana y componente lienzo.

comprobación de sintaxis. Verifica que la sintaxis de cada línea sea correcta mientras se edita el código fuente. Conello pueden evitarse errores de compilación. Esta opción puede activarse o desactivarse. Puede visualizarse sólodeterminados tipos de especificación, como especificaciones C, o una línea con una serie específica.

Conectividad de Baes de Datos Java (JDBC). Estándar del sector para la conectividad independiente de la base dedatos entre Java y una amplia gama de bases de datos. JDBC proporciona una interfaz de programación deaplicaciones (API) a nivel de llamada para el acceso a bases de datos basado en SQL.

conector. Función creada por el usuario o un proveedor externo que se puede utilizar en los programas VARPG.

CONFIG.SYS. Archivo de configuración, ubicado en el directorio raíz de la unidad de arranque, para los sistemasoperativos DOS, OS/2 o Windows. Contiene información necesaria para instalar y ejecutar hardware y software.

configuración. Manera en que el hardware y el software de un sistema de proceso de información estánorganizados y se conectan entre sí (T).

construir. Proceso por el que las diversas partes de un código fuente que forman los componentes lógicos de unaaplicación VARPG se compilan y enlazan para producir una versión ejecutable de la aplicación.

conversación DDE. El intercambio de datos entre un cliente DDE y un servidor DDE. Véase también conversación deenlace estático y conversación de enlace dinámico.

conversación de enlace dinámico. En DDE, actualización automática de un programa cliente por un programaservidor cuando los datos cambian en el servidor. Compárese con conversación de enlace estático

442 Programación con VisualAge RPG

Page 461: c 0924494

conversación de enlace estático. En DDE, petición explícita efectuada por un programa cliente a un programaservidor. El programa servidor responde a la petición. Compárese con conversación de enlace dinámico.

cuaderno de propiedades. Representación gráfica que se asemeja a un cuaderno enlazado que contiene páginasseparadas en secciones por páginas separadoras. Seleccione los separadores de un cuaderno para ir de una sección aotra.

cursor. Indicación visible de la posición en la que aparecerá la interacción de usuario con el teclado.

DDBCS. Juego de caracteres de doble byte.

DDE. Intercambio de datos dinámico.

definición de interfaz de procedimiento. Repetición de la información prototipo dentro de la definición de unprocedimiento. Se utiliza para declarar los parámetros de entrada para el procedimiento y para garantizar que ladefinición interna del procedimiento es coherente con la definición externa (el prototipo)

directorio destino. Directorio en el que se almacena la aplicación VARPG compilada después de una creación.Compárese con carpeta destino.

directorio fuente. Directorio en el que se almacenan todos los archivos fuente para una aplicación VARPG.

Diseñador GUI. Conjunto de herramientas utilizadas para crear interfaces arrastrando y soltando componentes dela paleta de componentes a la ventana de diseño.

DLL. Biblioteca de enlace dinámico.

doble pulsación. Pulsar un botón dos veces rápidamente.

EEBCDIC. Código de intercambio decimal binario ampliado. Juego de caracteres de 256 caracteres de 8 bits.

edición directa. Utilización de procedimientos que permiten a un usuario trabajar con un objeto arrastrándolo conun ratón o interactuando con su menú emergente.

elemento. En intercambio de datos dinámico, una unidad de datos. Por ejemplo, la posición de la casilla superiorizquierda en una hoja de cálculo es fila 1, columna 1. Se puede hacer referencia a la posición de la casilla como elelemento R1C1.

eliminar referencia. Acción de suprimir la asociación entre un componente y un campo de base de datos deAS/400.

énfasis. Resaltado del cambio de color u otra indicación visible de condiciones relativas a un objeto o una opciónque afecta a la capacidad del usuario de interactuar con ese objeto u opción. El énfasis también puede proporcionar aun usuario información adicional sobre el estado de una opción o un objeto.

entrada/salida (E/S). Datos proporcionados al sistema o datos que resultan del proceso del sistema.

estación de trabajo. Dispositivo que permite a un usuario efectuar trabajos. Véase también estación de trabajoprogramable.

estación de trabajo programable (PWS). Estación de trabajo que tiene posibilidades de proceso y que permite a unusuario modificar sus funciones.

evento. Señal generada como resultado de una modificación en el estado de un componente. Por ejemplo, alaccionar un pulsador se genera el evento Press.

evento de enlace. Evento que un componente destino recibe siempre que cambia el estado de un componentefuente.

Glosario 443

Page 462: c 0924494

excepción. (1) En lenguajes de programación, una situación anormal que se da durante la ejecución, que puedeocasionar una desviación de la secuencia normal de ejecución, para la que existen recursos en los lenguajes deprogramación a fin de definirla, activarla, reconocerla, ignorarla y manejarla. (I) (2) En VisualAge RPG, un evento osituación que impide, o puede impedir, que una acción solicitada por un usuario concluya tal como éste espera. Lasexcepciones tienen lugar cuando un producto no puede interpretar la entrada de un usuario.

EXE. Extensión de un archivo ejecutable.

exportar. Función que convierte un archivo interno en un formato de archivo estándar para utilizarlo fuera de laaplicación. Compárese con importar.

Ffoco. Sinónimo de foco de entrada.

foco de entrada. Área de una ventana en la que la interacción del usuario puede tener lugar desde el teclado odesde el ratón.

IICO. Extensión de archivo de un archivo de icono.

icono. Representación gráfica de un objeto, que se compone de una imagen, un fondo de imagen y una etiqueta.

importar. Función que convierte objetos de archivo de pantalla de AS/400 al componente VARPG adecuado.Compárese con exportar.

indicador de progreso. Uno o más controles utilizados para informar a un usuario sobre el curso de un proceso.

índice. Identificador de una entrada en componentes de VARPG como, por ejemplo, recuadros de lista o recuadrosde combinación.

INI. Extensión de archivo para un archivo del sistema operativo OS/2 o Windows que contiene informaciónespecífica de la aplicación que necesita conservarse de una llamada de una aplicación a otra.

intercambio de datos dinámicos (DDE). Intercambio de datos entre programas o entre un programa y un objeto dearchivo de datos. Cualquier cambio efectuado en la información de un programa o una sesión se aplica a los datosidénticos creados por el otro programa. Véase también conversación DDE, cliente DDE y servidor DDE.

Interfaz de programación de aplicaciones (API). Interfaz funcional suministrada por el sistema operativo o unprograma bajo licencia que se solicita por separado, que permite que un programa de aplicación escrito en unlenguaje de alto nivel pueda utilizar datos o funciones específicas del sistema operativo o del programa bajo licencia.

interfaz de usuario gráfica (GUI). Tipo de interfaz de usuario que proporciona las ventajas de los gráficos de altaresolución. Una interfaz gráfica de usuario incluye una combinación de gráficos, el paradigma de acción de objeto, eluso de dispositivos de puntero, barras de menú y otros menús, solapamiento de ventanas e iconos.

Interfaz Nativa de Java (JNI). Interfaz de programación que permite al código Java que se ejecuta dentro de unaMáquina Virtual Java (JVM) interoperar con las funciones escritas en otros lenguajes de programación.

IPF. Recurso de Presentación de Información.

JJava. Lenguaje de programación orientado a objeto para código interpretado portátil que soporta la interacción entreobjetos remotos. Java y sus especificaciones han sido desarrolladas por Sun Microsystems, Incorporated.

JavaBean. En Java, un modelo de componente reutilizable, portátil e independiente de la plataforma.

Java Runtime Environment (JRE). Subconjunto del Kit de desarrollo Java para los usuarios finales y desarrolladoresque deseen redistribuir el JRE. El JRE consiste en la Máquina Virtual Java, las Clases de Núcleo de Java y los archivosde soporte.

444 Programación con VisualAge RPG

Page 463: c 0924494

Java 2 Software Development Kit (J2SDK). Software que distribuye Sun Microsystems a los desarrolladores deJava. Este software incluye el interpretador Java, clases Java y herramientas de desarrollo Java. Las herramientas dedesarrollo incluyen un compilador, un depurador, un desensamblador, un AppletViewer, un generador de archivos deapéndice y un generador de documentación.

juego de caracteres de doble byte (DBCS). Juego de caracteres en el que cada carácter se representa mediante 2bytes. Algunos idiomas como el japonés, el chino o el coreano, que contienen más símbolos de los que puedenrepresentarse mediante los 256 puntos de código, necesitan el juego de caracteres de doble byte. Puesto que cadacarácter necesita 2 bytes, la escritura, la visualización y la impresión de caracteres DBCS necesita hardware yprogramas que soporten DBCS. El sistema soporta cuatro juegos de caracteres de doble byte: japonés, coreano, chinosimplificado y chino tradicional. Compárese con juego de caracteres de un solo byte (SBCS).

juego de caracteres de un solo byte (SBCS). Juego de caracteres en el que cada carácter se representa mediante unbyte. Compárese con juego de caracteres de doble byte (DBCS).

Llínea de ejecución. La unidad más pequeña de operación que puede efectuarse dentro de un proceso.

lista desplegable. Campo de una sola selección en el que sólo puede verse la opción actual. Las demás opcionespermanecen ocultas hasta que el usuario realiza una acción específica para visualiza el recuadro de lista que lascontiene.

lugar de trabajo. Área que ocupa toda la pantalla y contiene todos los objetos que componen la interfaz del usuario.

MMáquina Virtual Java (JVM). La parte del Java Runtime Environment (JRE) responsable de interpretar bytecodes deJava.

marcador de grupo. Marcador que identifica un componente como el primero de un grupo. Cuando el usuariodesplaza el cursor por un grupo de componentes y llega al último, el cursor vuelve a la primera parte del grupo.

mensaje. (1) Información no solicitada por un usuario pero visualizada por un producto como respuesta a unevento no esperado o cuando se produce algo no deseado. (2) Comunicación enviada por una persona o unprograma a otra persona u otro programa.

menú. Lista de opciones que pueden aplicarse a un objeto. Un menú puede contener opciones que no esténdisponibles para ser seleccionadas en determinados contextos. Estas opciones están atenuadas.

menú desplegable. Menú que aparece al seleccionar una opción en una barra de menú o a partir del símbolo delmenú del sistema. Las opciones de un menú desplegable están relacionadas entre sí.

menú emergente. Menú que, cuando se solicita, aparece junto al objeto con el que está asociado. Contiene opcionesadecuadas para el objeto en su contexto actual.

MID. Extensión de archivo de un archivo MIDI.

migrar. (1) Mover a un sistema operativo modificado, generalmente a un nuevo release o versión de un sistema. (2)Mover datos desde una jerarquía de almacenamiento a otra.

módulo EXE. Un módulo EXE consta de un procedimiento principal y subprocedimientos. Se crea cuando la palabraclave EXE está presente en la especificación de control. Todas las subrutinas (BEGSR) deben ser locales a unprocedimiento. El EXE debe contener un procedimiento cuyo nombre coincida con el nombre del archivo fuente. Esteserá el punto de entrada principal para el EXE; es decir, el procedimiento principal.

módulo NOMAIN. Módulo que contiene solamente subprocedimientos. No contiene ninguna acción o subrutina deusuario autónoma. Un módulo NOMAIN se crea cuando la palabra clave NOMAIN se encuentra en la especificaciónde control.

Glosario 445

Page 464: c 0924494

Nnemotécnico. Un solo carácter, dentro del texto de una opción, identificado por un subrayado debajo de él. Véasetambién selección nemotécnica.

nivel del graduador. Indicador visual en el graduador que un usuario puede mover para modificar el valornumérico.

Oobjeto. (1) Espacio de almacenamiento con nombre que consiste en un conjunto de características que describen elespacio de almacenamiento en sí y, en algunos casos, datos. Un objeto es algo que existe en el almacenamiento yocupa parte de su espacio, y en el que se pueden efectuar operaciones. Algunos ejemplos de objetos son: programas,archivos, bibliotecas y carpetas. (2) Componente visual de una interfaz de usuario con el que un usuario puedeefectuar una tarea. Un objeto puede aparecer como texto o como un icono.

objeto de datos. Objeto que transporta información, como texto, gráficos, audio o vídeo.

Ppaleta de colores. Conjunto de colores que puede utilizarse para cambiar el color de cualquier componente en laGUI de la aplicación.

paleta de componentes. El grupo de componentes más adecuado para construir la interfaz gráfica de usuario actualpara una aplicación. Cuando finaliza la GUI, puede vaciar la paleta y añadir los componentes del catálogo decomponentes que necesite para la siguiente aplicación.

paleta de fonts. Conjunto de fonts que puede utilizarse para cambiar el font de un componente en la GUI de laaplicación.

panel de navegación. Grupo de botones que se pueden utilizar para controlar la selección visible de registros en unsubarchivo.

paquete. Función utilizada para reunir todos los componentes de una aplicación VARPG para su distribución.

paradigma acción-objeto. Patrón de interacción en el que un usuario selecciona un objeto y a continuaciónselecciona una acción para aplicarla a ese objeto.

procedimiento. Un procedimiento es cualquier parte del código a la que pueda llamarse mediante la operaciónCALLP.

procedimiento principal. Un procedimiento principal es un subprocedimiento que puede especificarse comoprocedimiento de entrada del programa y que recibe el control cuando se le llama por primera vez. El procedimientoprincipal sólo se genera cuando se crea un EXE. Consulte módulo EXE

programación orientada a objetos. Método para estructurar programas como clases organizadas jerárquicamenteque describen los datos y las operaciones de objetos que pueden interactuar con otros objetos. (T)

programa destino. Objeto que el proyecto ha de crear, como una biblioteca de enlace dinámico (DLL).

programa de utilidad DLL. Véase módulo NOMAIN

programa objeto. Programa destino adecuado para ser ejecutado. Un programa objeto puede o no necesitar enlace.(T)

prototipo. Un prototipo es una definición de la interfaz de llamadas. Incluye información como, por ejemplo, si lallamada está enlazada (procedimiento) o es dinámica (programa), el nombre externo, el número y la naturaleza de losparámetros, qué parámetros deben ser pasados y el tipo de datos de cualquier valor de retorno (para unprocedimiento)

proyecto. Conjunto de datos y acciones completo necesarios para construir un destino único, como una biblioteca deenlace dinámico (DLL) o un archivo ejecutable (EXE).

446 Programación con VisualAge RPG

Page 465: c 0924494

pulsar. Pulsar y liberar un botón del ratón sin mover el puntero fuera de la opción o del objeto. Véase también doblepulsación.

puntero del ratón. Sinónimo de cursor.

PWS. Estación de trabajo programable.

Rratón. Dispositivo con uno o más pulsadores que se utilizan para colocar un puntero en la pantalla sin usar elteclado. Se utiliza para seleccionar una opción o una función que se ha de efectuar o para llevar a cabo operacionesen la pantalla, como dibujar líneas y arrastrarlas de una posición a otra.

recuadro de combinación. Control que combina las funciones de un campo de entrada y de un recuadro de lista.Un recuadro de combinación contiene una lista de objetos por los que el usuario puede desplazarse y seleccionarpara completar el campo de entrada. Si lo desea, el usuario también puede escribir texto directamente en el campo deentrada. En VisualAge RPG, se señala y pulsa un componente recuadro de combinación de la paleta de componenteso del catálogo de componentes y se suelta en una ventana de diseño.

recuadro de combinación desplegable. Tipo de recuadro de combinación en la que un recuadro de lista está ocultohasta que un usuario realiza una acción específica para visualizarlo.

Recurso de Presentación de Información (IPF). Herramienta utilizada para crear ayuda en línea en una estación detrabajo programable.

resaltado de símbolos. Mejora la legibilidad del código. Puede configurar el resaltado de diferentes elementos dellenguaje con diferentes colores o fonts para identificar las estructuras del programa. Puede activar o desactivar elresaltado de símbolos.

SSBCS. Juego de caracteres de un solo byte.

sección fuente principal. En un programa VARPG, la sección que contiene todas las definiciones globales para unmódulo. Para un componente lógico, esta sección también incluye la acción y las subrutinas de usuario.

selección nemotécnica. Método de selección en el que un usuario selecciona una opción tecleando el nemotécnicode esa opción.

señalar y pulsar. (1) Método de selección que se utiliza para copiar un componente de la paleta o el catálogo decomponentes en la ventana de diseño, la vista de iconos o la vista de árbol de la GUI. (2) Para colocar uncomponente en cualquiera de las vistas, señale y pulse el componente; después, mueva el cursor a la ventana elegiday señale y suelte el componente donde desea que aparezca. En las vistas de iconos y de árbol, el componente secolocará en el componente padre, y tendrá que moverlo al lugar donde le interese que aparezca en la ventana dediseño.

servidor. Sistema de una red que maneja las peticiones de otro sistema, llamado cliente.

servidor DDE. Aplicación que proporciona datos a otra aplicación habilitada por DDE. Compárese con cliente DDE.Véase también conversación DDE.

sistema operativo. Grupo de programas del sistema que controlan la operación general de un sistema.

solicitud. (1) Mensaje visual o audible enviado por un programa para solicitar la respuesta de un usuario. (T) (2)Símbolo o mensaje que se visualiza para solicitar una entrada del usuario o proporcionar información operativa. Elusuario debe responder a la solicitud para poder proseguir.

SSL. Capa de Sockets Segura.

submenú. Menú que aparece al seleccionar una opción en cascada en otro menú y que contiene opcionesrelacionadas con dicho menú. Los submenús se utilizan para reducir la longitud de un menú desplegable o de unmenú emergente. Véase también componente submenú.

Glosario 447

Page 466: c 0924494

subprocedimiento. Procedimiento especificado después de la sección fuente principal. Debe tener un prototipocorrespondiente en las especificaciones de definición de la sección fuente principal.

subrutina de acción. Lógica que se escribe para responder a un evento específico.

Ttema. En intercambio de datos dinámico (DDE), el juego de datos que es el sujeto de una conversación DDE.

tope de tabulador. Atributo utilizado para establecer un tope de tabulador para un componente de manera que losusuarios pueden proporcionarle foco cuando utilizan el tabulador para moverse por la interfaz.

Vvalor por omisión. Valor que el sistema o un programa proporciona o presupone automáticamente cuando elusuario no especifica ninguno. El valor por omisión puede asignarse a un pulsador o a un pulsador gráfico.

ventana activa. Ventana con la que un usuario interactúa actualmente. Esta es la ventana que recibe la entrada delteclado.

ventana de diseño. Ventana en el diseñador GUI en la que se colocan componentes para crear una interfaz deusuario.

ventana emergente. Ventana movible, de tamaño fijo, en la que un usuario proporciona información necesaria parauna aplicación de manera que puede continuar procesando una petición de usuario. Sinónimo de ventana secundaria.

ventana inactiva. Ventana que no puede recibir entrada de teclado en un momento dado.

ventana primaria. Ventana en la que tiene lugar la interacción principal entre el usuario y la aplicación. Sinónimo deventana principal.

ventana principal. Véase ventana primaria.

ventana secundaria. Ventana que contiene información que depende de la información de una ventana primaria yse utiliza para complementar la interacción en dicha ventana. Véase también ventana primaria. Sinónimo de ventanaemergente.

vista de árbol. Visualización del contenido de un objeto de manera jerárquica.

vista de detalles. Vista de contenido estándar en la que un icono pequeño se combina con texto para proporcionarinformación descriptiva sobre un objeto.

vista de iconos. Vista de contenido estándar en la que cada objeto contenido en un contenedor se visualiza como unicono.

WWAV. Extensión de archivo de un archivo de ondas.

448 Programación con VisualAge RPG

Page 467: c 0924494

Bibliografía

Para obtener información adicional sobre temas relacionados con VisualAge RPG yCODE (Cooperative Development Environment) para AS/400, consulte lassiguientes publicaciones de IBM:

Manuales de WebSphere Development Tools para AS/400:

*Nota: Se han actualizado todas las versiones en línea de las publicaciones deWebSphere Development Tools para AS/400. Las publicaciones cuyonúmero de pedido está marcado con un asterisco (*) no se han vuelto aimprimir en este release.

v Iniciación a VisualAge RPG y CODE/400, SC10-3287-01 (SC09-2625-01),proporciona información sobre WebSphere Development Tools para AS/400,dando una visión general de las características de CODE/400 y VARPG, decómo funcionan juntas y de las ventajas empresariales que se obtienen alutilizarlas.

Manuales de VisualAge RPG:v Iniciación a VisualAge RPG y CODE/400, SC10-3287-01 (SC09-2625-01)*, describe

los conceptos y las tareas de VARPG que se realizan mientras se utilizaVisualAge RPG.

v VisualAge RPG Manual de consulta del lenguaje, SC10-3066-01 (SC09-2451-01)*,proporciona información de consulta sobre el lenguaje y el compilador deVARPG.

v VisualAge RPG Manual de consulta de componentes, SC10-3065-02 (SC09-2450-02)*,proporciona una descripción de cada componente, atributo de componente,evento de componente, atributo de componente y atributo de evento de VARPG.Es un manual de consulta para todos aquellos que desarrollan aplicaciones conVisualAge RPG.

v Programación con VisualAge para RPG, SC10-3067-02 (SC09-2449-02)*, contieneinformación específica sobre cómo crear aplicaciones con VisualAge RPG.Describe los pasos que debe seguir en cada fase del ciclo de desarrollo de laaplicación, desde el diseño hasta el empaquetado y la distribución. Se incluyenejemplos de programación para clarificar los conceptos y el proceso dedesarrollo de aplicaciones VARPG.

v Java for RPG Programmers es una introducción al lenguaje Java (y RPG IV)mediante la comparación con el lenguaje RPG. Se trata de un comienzo muyapropiado en el mundo de Java. También incluye una guía de aprendizajeinteractiva en formato CD sobre Java y VisualAge para Java, mediante MINDQ.

v Experience RPG IV Tutorial es una guía de aprendizaje interactiva en formato CDque enseña RPG IV e ILE, paso a paso y de un modo divertido. Se trata de unmanual con preguntas y ejercicios que ayudan a adquirir experiencia prácticacon esta nueva y apasionante versión de RPG.

v Otra publicación que no es de IBM interesante para los usuarios de VisualAgeRPG es VisualAge for RPG by Example.

Información y publicaciones del AS/400:v Si tiene acceso a Internet, puede obtener otra información y publicaciones del

AS/400 en uno de los siguientes sitios Web:http://www.as400.ibm.com/infocenter

http://publib.boulder.ibm.com/pubs/html/as400/infocenter.htm

© Copyright IBM Corp. 1994, 2000 449

Page 468: c 0924494

Para obtener una versión en copia software de las publicaciones de AS/400,consulte la publicación CD-ROM AS/400e Biblioteca en soporte software,SK3T-1325-04 (SK3T-0118-04).

Manuales de Gestor para el Desarrollo de Aplicaciones ADM:v ADTS/400: Gestor para el Desarrollo de Aplicaciones ADM Introducción y guía de

planificacion, GC10-9401-00 (GC09-1807-00), describe los conceptos básicos y laplanificación necesaria para hacer un uso efectivo de la función Gestor para elDesarrollo de Aplicaciones ADM.

v ADTS/400: Gestor para el Desarrollo de Aplicaciones ADM Guía del Usuario,SC10-9609-01 (SC09-2133-01), describe cómo crear y gestionar proyectosdefinidos para la función Gestor para el Desarrollo de Aplicaciones ADM.

v ADTS/400: Gestor para el Desarrollo de Aplicaciones ADM Guía de autoaprendizaje,SC10-9610-00 (SC09-2138-00), proporciona experiencia práctica en la utilizaciónde la función Gestor para el Desarrollo de Aplicaciones ADM del productoADTS para OS/400. Esta guía muestra cómo utilizar la función Gestor para elDesarrollo de Aplicaciones ADM guiándole a través de una serie de ejerciciospaso a paso.

v ADTS/400: Application Development Manager API Reference, SC09-2180-00, describecómo los programadores de aplicaciones pueden escribir su propia interfaz parala función Gestor para el Desarrollo de Aplicaciones ADM.

Manual Recurso de presentación de información (IPF):v Information Presentation Facility Programming Guide G25H-7110, describe los

elementos que componen el IPF (Recurso de presentación de información). IPFes una herramienta que soporta el diseño y el desarrollo de documentos en líneay de recursos de ayuda en línea.

Manuales de SQL:v IBM SQL Reference Version 2 SC26-8416, Volumen 2, compara los recursos de

– DB2– SQL/DS™

– DB2/400™

– DB2/6000™

– IBM SQL– ISO-ANSI (SQL92E)– X/Open™ (XPG4-SQL).

v DB2 Universal Database Administration Guide S10J-8157, proporciona lainformación necesaria para utilizar y administrar el producto DB2.

v DB2 Universal Database Embedded SQL Programming Guide S10J-8158, describecómo diseñar y codificar programas de aplicación para acceder a los servidoresde la familia DB2 Client/Server (como DB2 o DB2/400). Contiene informacióndetallada sobre la utilización del SQL (Lenguaje de Consulta Estructurada) yllamadas de API en las aplicaciones.

450 Programación con VisualAge RPG

Page 469: c 0924494

Avisos

Esta información se ha elaborado para productos y servicios que se ofrecen enEstados Unidos. Es posible que IBM no ofrezca todos los productos, servicios ocaracterísticas que se tratan en este documento en otros países. Consulte con elrepresentante local de IBM para obtener información sobre los productos yservicios que están disponibles en su área en la actualidad. Ninguna referenciahecha en esta publicación a un producto, programa o servicio de IBM pretendeafirmar ni implicar que sólo pueda utilizarse dicho producto, programa o serviciode IBM. Puede utilizarse cualquier producto, programa o servicio funcionalmenteequivalente y que no infrinja ninguno de los derechos de propiedad intelectual deIBM. Sin embargo, es responsabilidad del usuario evaluar y verificar elfuncionamiento de los productos, programas o servicios que no sean de IBM.

IBM puede tener patentes o solicitudes de patente pendientes acerca del tema deeste documento. La entrega de este documento no le otorga ninguna licencia sobredichas patentes. Puede enviar consultas sobre licencias, por escrito, a:

Director of LicensingIntellectual Property & LicensingInternational Business Machines CorporationNorth Castle Drive, MD - NC119Armonk, New York 10504-1785EE.UU.

El siguiente párrafo no es aplicable en el Reino Unido ni en ningún otro paísdonde tales estipulaciones sean contradictorias con la legislación local:INTERNATIONAL BUSINESS MACHINES CORPORATION PROPORCIONAESTA PUBLICACIÓN “ TAL CUAL”, SIN NINGÚN TIPO DE GARANTÍA,EXPLÍCITA O IMPLÍCITA, INCLUYENDO, PERO SIN LIMITARSE A, LASGARANTÍAS IMPLÍCITAS DE NO VULNERACIÓN, COMERCIALIZACIÓN EIDONEIDAD PARA UNA FINALIDAD DETERMINADA. En determinados paísesno se permite la declaración de limitación de responsabilidad de las garantíasexpresas ni implícitas en determinadas transacciones, por lo tanto, esta declaraciónpuede no ser procedente en su caso.

Esta información puede contener inexactitudes técnicas o errores tipográficos. Seefectúan cambios periódicos en la información contenida en este documento; talescambios se incorporarán en nuevas ediciones de la publicación. IBM puede hacermejoras y/o modificaciones en los productos y/o programas descritos en estapublicación en cualquier momento sin previo aviso.

Las referencias hechas en esta información a páginas Web de terceros seproporcionan sólo como gentileza para los usuarios y de ninguna manera puedeinterpretarse que IBM avala esas páginas Web. El material de estas páginas Web noforma parte del material para este producto de IBM y el usuario será el únicoresponsable del uso de estas ubicaciones Web.

Los poseedores de una licencia de este programa que deseen obtener informaciónal respecto con el fin de permitir: (i) el intercambio de información entreprogramas creados de manera independiente y otros programas (incluido éste) y(ii) la utilización mutua de la información que se ha intercambiado, deben ponerseen contacto con IBM en la siguiente dirección:

© Copyright IBM Corp. 1994, 2000 451

Page 470: c 0924494

IBM Canada Ltd.Department 0711150 Eglinton Avenue EastToronto, Ontario M3C 1H7Canadá

Dicha información estará disponible de acuerdo con los términos y condicionesoportunos, que en algunos casos puede incluir el pago de una cantidad.

IBM proporciona el programa bajo licencia descrito en esta información y todo elmaterial bajo licencia disponible para él según los términos del Contrato de ClienteIBM, Contrato de Licencia de Programa Internacional IBM o cualquier contratoequivalente entre IBM y el cliente.

Información de interfaz de programaciónEsta publicación pretende ayudarle a crear y gestionar aplicaciones e interfaces deusuario VisualAge RPG en la estación de trabajo, en un entorno cliente/servidor.Esta publicación documenta la interfaz de programación de uso general y lainformación de guía asociada que proporciona VisualAge RPG y CODE/400.

Marcas registradas y marcas de servicioLos siguientes términos son marcas registradas de International Business MachinesCorporation en Estados Unidos y/o en otros países:

Application System/400 AS/400 AS/400eCommon User Access CUA DATABASE 2DB2 DB2 Connect DB2 Universal DatabaseIBM OS/400 SQL/DSVisualAge 400

Java y todas las marcas registradas derivadas de Java son marcas registradas deSun Microsystems, Inc. en Estados Unidos y/u otros países.

Lotus es marca registrada de Lotus Development en Estados Unidos y/u otrospaíses.

ActiveX, Microsoft, Windows y Windows NT son marcas registradas de MicrosoftCorporation en Estados Unidos y/o en otros países.

Otros nombres de empresas, productos y servicios pueden ser marcas registradas omarcas de servicio de terceros.

452 Programación con VisualAge RPG

Page 471: c 0924494

Índice

CaracteresEspeciales%GETATR, utilización 25%SETATR, utilización 25*INZSR 261.MID, archivo

proceso por componentes medios 99*TERMSR 261.WAV, archivo

proceso por componentes medios 99

Aacceso a archivos de imágenes en tiempo

de construcción 234actualizar registro de subarchivo

para componentes subarchivo 153AddItemEnd, atributo 145AddMsgId, atributo 106AddMstTxt, atributo 106AddRcd, atributo 65agrupación de botones de selección,

ejemplo 136alteraciones temporales

acceso a archivos de base de datos deAS/400 192

acceso a áreas de datos deAS/400 191

llamada a programas AS/400 262alteraciones temporales de área de

datos 191aplicación

actualización 407eliminar 407empaquetado 399instalación 407volver a empaquetar 407volver a instalar 407

aplicación Video Catalogadición de ayuda en línea 15adición de mensajes 15creación de la ventana Comedy 7creación de la ventana Preview 11descripción de 3diseño 5ejecutar 4instalación 3

aplicaciones, cliente ligero 417archivo .EVT, descripción 413archivo .HLP, descripción 413archivo .IPF, descripción 413archivo .IPM, descripción 413archivo .LIB, descripción 413archivo .LST, descripción 413archivo .ODF, descripción 413archivo .ODX, descripción 413archivo .RST, descripción 413archivo .TXC, descripción 413archivo .TXM, descripción 413

archivo .VPF, descripción 413archivo .VPG, descripción 413archivo de imagen

para componentes imagen 81utilización 233

archivos de aplicacióndescripción 413nombrearchivo.DLL 218, 413nombrearchivo.EVT 413nombrearchivo.EXE 413nombrearchivo.HLP 413nombrearchivo.IPF 413nombrearchivo.IPM 413nombrearchivo.LIB 413nombrearchivo.LST 413nombrearchivo.ODF 413nombrearchivo.ODX 413nombrearchivo.RST 189, 413nombrearchivo.TXC 413nombrearchivo.TXM 413nombrearchivo.VPF 413nombrearchivo.VPG 413

archivos de pantallacolor de componentes

convertidos 211formatos de registro de pantalla 207palabras clave de archivos de

pantalla 209reutilización 206, 207

archivos de sonido, utilización 233Arrange, atributo 67AS/400

acceso a archivos en el sistemaAS/400 34

creación de archivos de datos para losprogramas de ejemplo 34

mensajes para traducir 250nombrearchivo.RST 413reutilizar aplicaciones de 201reutilizar ayuda UIM 212

atributo AddLinkcontrol del componente medios 100para componentes panel de

medios 101atributo AddOffset 111atributo AllowLink

habilitación del control panel demedios estableciendo 100

para componentes panel demedios 101

atributo BackColor, usos comunes de 37atributo Bottom, usos comunes de 37atributo Count

para componentes contenedor 66para componentes recuadro de

lista 92para componentes subarchivo 154

atributo Checkedpara componentes opción de

menú 104

atributo Checked (continuación)para componentes recuadro de

selección 55atributo DDEAddLink

utilización 255atributo DDEMode 255atributo del sistema %DspHeight 27, 38atributo del sistema %DspWidth 27, 38atributo DeSelect

para componentes recuadro delista 91, 92

atributo DragEnable 41atributo DropEnable 41atributo Enabled

para componentes campo deentrada 74

para componentes edición demúltiples líneas 111

para componentes opción demenú 105

usos comunes de 37atributo FileName

para componentes imagen 82para componentes medios 99, 233para componentes pulsador

gráfico 78atributo Focus, usos comunes de 38atributo ForeColor, usos comunes de 37atributo ForeMix, usos comunes de 37atributo GetItem 92atributo Height

para componentes recuadro decontorno 131

usos comunes de 37atributo Index

para componentes recuadro decombinación 59

para componentes recuadro delista 92

para componentes subarchivo 155atributo InfoLabel 39atributo InsertItem

para componentes recuadro decombinación 58

para componentes recuadro delista 91

atributo InsertLine 110atributo Interval 167atributo Label

finalidad 30para componentes opción de

menú 104para componentes pulsador 134para componentes recuadro de

grupo 79para componentes texto estático 149usos comunes de 39

atributo Left, usos comunes de 37atributo LineNumber 110

para componentes edición demúltiples líneas 110

© Copyright IBM Corp. 1994, 2000 453

Page 472: c 0924494

atributo Multiplier 167atributo MultSelect

para componentes recuadro delista 75, 90

para componentes subarchivo 152atributo Panel 82atributo PanelItem 102atributo ParentName, usos comunes

de 35atributo PartName, usos comunes de 35atributo PartType, usos comunes de 35atributo Position

establecer 100para componentes panel de

medios 102atributo ReadOnly

para componentes campo deentrada 74

para componentes edición demúltiples líneas 111

para componentes recuadro decombinación 59

para componentes selectorcíclico 146

atributo Selectedpara componentes recuadro de

combinación 59para componentes recuadro de

lista 91, 92atributo Sequence

para componentes recuadro decombinación 58

para componentes recuadro delista 90

atributo SetItempara componentes recuadro de

combinación 59para componentes recuadro de

lista 91atributo SetTop

para componentes recuadro decombinación 59

para componentes recuadro delista 91

atributo TabLabel 39atributo Text 110atributo TextEnd 111atributo TextSelect 111atributo TextStart 111atributo TickLabel

para componentes graduador 139atributo TimerMode 168atributo UserData, usos comunes de 39atributo Value

para componentes graduador 139para componentes selector

cíclico 146para componentes temporizador 168

atributo Visiblepara componentes de ventana 176para componentes temporizador 167usos comunes de 38

atributo Volumepara componentes medios 100para componentes panel de

medios 102

atributo Widthpara componentes recuadro de

contorno 131usos comunes de 37

atributos

AddItemEnd 145AddLink 100, 101AddMsgId 106AddMsgTxt 106AddOffset 111AddRcd 65AllowLink 100, 101Arrange 67AudioMode 100BackColor 37BackMix 37, 140Bottom 37ColNumber 66, 155comprobación de atributos de evento

y de sistema 27Count 66, 92, 154CharOffSet 111Checked 55, 104DDEMode 255DeSelect 59, 91, 92DragEnable 41DropEnable 41Enabled 37, 74, 105, 111FileName 78, 82, 99, 233FirstSel 59Focus 38FontName 149FontSize 149ForeColor 37ForeMix 37GetItem 92GetNewID 65GetRcdText 65Height 37, 131Index 59, 92, 155InfoLabel 39InsertItem 58, 91InsertLine 110InsertMode 73Interval 167Label 39, 79, 104, 134, 149Left 37LineNumber 110Masked 74Maximum 145Minimum 145MsgSubText 107Multiplier 167obtener y establecer 25OpenEdit 155OpenImmediately 176, 177Panel 82PanelItem 102para componentes barra de

desplazamiento horizontal 80para componentes barra de

desplazamiento vertical 174para componentes barra de

estado 151para componentes barra de

progreso 133para componentes bean Java 87

atributos (continuación)para componentes botón de

selección 136para componentes campo de

entrada 72para componentes cliente DDE 71para componentes contenedor 64para componentes control de

animación 50para componentes cuaderno 115para componentes de ActiveX 47para componentes de

posicionamiento 37para componentes edición de

múltiples líneas 110para componentes graduador 139para componentes imagen 82para componentes interfaz

ODBC/JDBC 119para componentes lienzo 54para componentes lienzo de

cuaderno 117para componentes menú

emergente 132para componentes opción de

menú 104para componentes página de

cuaderno 116para componentes panel de

medios 101para componentes pulsador 134para componentes pulsador

gráfico 78para componentes recuadro de

combinación 57, 58para componentes recuadro de

contorno 131para componentes recuadro de

grupo 79para componentes recuadro de

lista 75, 90para componentes recuadro de

selección 55para componentes referencia a

componente lógico 62para componentes subarchivo 152para componentes subarchivo de

mensajes 106para componentes submenú 166para componentes temporizador 167para componentes texto estático 149para componentes ventana con

lienzo 175, 176ParentName 35PartName 35PartType 35Position 100, 102ReadOnly 59, 74, 111, 146RecordID 66RemoveItem 59, 91RemoveMsg 107RemoveRcd 67Selected 59, 91, 92SelectItem 61Sequence 58, 90SetItem 59, 91SetRcdIcon 67

454 Programación con VisualAge RPG

Page 473: c 0924494

atributos (continuación)SetRcdText 64SetTop 59, 91TabLabel 39Terminar al cerrar 182Text 59, 73, 110, 146TextEnd 111TextSelect 111TextStart 111TimerMode 168UserData 39Validate 73Value 139, 146, 168View 70Visible 38, 167, 176Volume 102Volumen 100Width 37, 131

atributos comunes, descripción de 35atributos de evento, utilización 26atributos del sistema

%DspHeight 27, 38%DspWidth 27, 38

AudioMode, atributo 100ayuda

adición de gráficos a 236creación de enlaces de hipertexto 237creación de un pulsador de

ayuda 236creación para Windows 239editar 212nombrearchivo.IPM 413nombrearchivo.VPF 413para aplicaciones Java 243planificación de la aplicación 19reutilizar UIM 212tipos de 236traducir 235

ayuda según el contexto 236

Bbarra de desplazamiento horizontal

atributos 80eventos 80finalidad 80

barra de desplazamiento verticalatributos 174eventos 174finalidad 174

barra de estado, componenteatributos 151eventos 151finalidad 151

barra de menúsatributos 103eventos 103finalidad 103

barra de progreso, componentefinalidad 133

bean Java, componenteatributos 87classpath, configuración 88crear 87finalidad 87JAR asociados 88propiedades y métodos 89

bibliografía 449

bitmaps, utilización 233bloqueo de archivos de base de datos de

AS/400 196BMP, archivo

utilización 81, 233botón de maximizar 178botón de minimizar 178buscar un mensaje

un mensaje 249

Ccalendario 51

finalidad 51cambio

el contenido de un campo durante ladepuración 224

la representación durante ladepuración 224

un valor de puntero durante lamodificación 226

variables, matrices y estructurasdurante la depuración 224

vistas del depurador 226cambio de la posición de los

componentes 178cambio del tamaño de las ventanas 178cambios de fuente java 278campo, componentes

nombres exclusivos 30campos de subarchivo ocultos 155CLEAR, código de operación

finalidad 30para componentes subarchivo 153

cliente DDEatributos 71determinar si está soportado por

programas 71eventos 71finalidad 71

clientes ligeros 417Close, evento 182código de operación BEGACT, respuesta

a eventos con 26código de operación CALL, ejemplo

de 262código de operación CALLB

llamada a funciones locales 255, 256código de operación ENDACT, respuesta

a eventos con 26código de operación READ (leer un

registro)archivos de base de datos 195finalidad 30

código de operación SETATR (estableceratributo)

para componentes imagen 82reflejar valores almacenados en la

pantalla 29código de operación STOP (detener un

componente lógico)descripción 261

código de operación WRITE (crearnuevos registros)

archivos de base de datos 195finalidad 30para componentes subarchivo 153

código de operación WRITE (crearnuevos registros) (continuación)

reflejar valores almacenados en lapantalla 29

código de tiempo de ejecuciónempaquetado 399instalación 407

código fuenteeditar 214nombrearchivo.VPG 413

códigos de edicióndefinido por el usuario 230finalidad 229formato de datos en formatos

predefinidos 229códigos de operación

CALLB 256CLEAR 153, 183CHAIN 153DELETE 153READ 73READC 153READS 153SETATR 82SHOWWIN 177START 62, 260STOP 260UPDATE 153WRITE 73, 153

ColNumber, atributo 66, 155color de componentes convertidos

después de la importación 211colores de componente

ejemplo de componentegraduador 140

usos comunes de 37compartir campos de programa, ejemplo

de componentes 31compilación de programas

nombrearchivo.EVT 413nombrearchivo.LST 413

Complete, evento 100componente *component

atributos 184eventos 184finalidad 184

Componente ActiveXatributos 47crear 47eventos 47, 49, 87finalidad 46métodos 48propiedades 47

componente botón de selecciónatributos 136ejemplo que muestra cómo

agrupar 136eventos 136finalidad 136

componente campo de entradaalmacenar valores de lectura 29alteración temporal de valores

definidos 29atributos 72borrar 183eventos 73finalidad 72

Índice 455

Page 474: c 0924494

componente campo de entrada(continuación)

inicio de componentes lógicos 260y transferencia de datos 41

componente de interfaz ODBC/JDBCacceder a los datos de una tabla 120atributos 119, 133conexión a una base de datos 119crear de un conjunto de registros 119eventos 119, 133finalidad 118recuperar filas de tabla 121tipos de datos 121

componente edición de múltiples líneasatributos 110ejemplo de 112eventos 110finalidad 110y transferencia de datos 41

componente elemento de menúatributos 104eventos 103, 104finalidad 104

componente pulsadoratributos 134eventos 134finalidad 134

componente pulsador gráficoatributos 78eventos 78finalidad 77

componente recuadro de combinaciónañadir y cambiar elementos 58atributos 57eliminación de elementos 59eventos 58finalidad 57orden de elementos 58recuperación de un elemento

seleccionado por usuario 59selección y deselección de

elementos 59y transferencia de datos 41

componente Recuadro de contornoatributos 131eventos 131finalidad 131

componente subarchivo de mensajesatributos 106ejemplo de 108eventos 106finalidad 106y transferencia de datos 41

componente texto estáticoalmacenar valores de lectura 29alteración temporal de valores

definidos 29atributos 149eventos 149finalidad 149nombres exclusivos 30y transferencia de datos 41

componente ventanaatributos 175eventos 175finalidad 175

componentes

*component 184ActiveX 46barra de desplazamiento

horizontal 80barra de desplazamiento vertical 174barra de estado 151barra de menús 103barra de progreso 133Bean Java 87botón de selección 136cambio de los colores de 37campo de entrada 72Cliente DDE 71colocación en diversas resoluciones de

monitor 38comunicación entre 253contenedor 64Contenedor 64control de animación 50cuaderno 115detener 261edición de múltiples líneas 110elemento de menú 104enlace 253graduador 139gráfica 75habilitación de componentes 37imagen 81iniciar 260interfaz ODBC/JDBC 118lienzo 53listado de eventos para un

componente 26marco de la ventana 175medios 99menú emergente 132página de cuaderno 116página de cuaderno con lienzo 117panel de medios 101posicionamiento 37pulsador 134pulsador gráfico 77recuadro de combinación 57Recuadro de combinación 57recuadro de contorno 131recuadro de grupo 79recuadro de lista 83, 90recuadro de selección 55referencia 25referencia a componente lógico 62Referencia a componente lógico 62selector cíclico 145soportar transferencia de datos 41subarchivo 152subarchivo de mensajes 106submenú 166temporizador 167texto estático 149ventana 175, 176

comprobación de nivel 196

conectores de proveedor

añadir 371crear 373gestionar 371invocar 371

contenedor, componenteatributos 64cambio de vistas de 67ejemplo de actualización de datos

en 66ejemplo de adición de registros a 66ejemplo de eliminar registros de 67eventos 64finalidad 64

control de animación, componenteatributos 50eventos 50finalidad 50

conversióncódigo fuente RPG utilizando

CVTRPGSRC 214Crear archivo de mensajes, programa de

utilidad 250cuaderno, componente

atributos 115eventos 115finalidad 115

CVTRPGSRC, herramienta de conversiónILE RPG/400 214

CHCHAIN (recuperación aleatoria de

archivo), código de operación 153Change, evento

para componentes graduador 140para componentes panel de

medios 102y componentes edición de múltiples

líneas 112CharOffset, atributo 111

DDELETE (suprimir registro), código de

operación 153depurador

cambio de vista 223Cargar aparición 218ejecución de pasos 222ejecución de pasos externos 222ejecución de pasos internos 222ejecución de un programa durante la

depuración 222ejecución del programa 223establecimiento de puntos de

interrupción 219, 221iniciar 217modificación de la

representación 224modificación de las vistas del

depurador 226modificación del contenido de un

campo 224puntos de interrupción 218retorno de recorrido 222selecciones de la barra de

herramientas 222visión general 217visualización de la pila 223visualización de la supervisión del

programa 223

456 Programación con VisualAge RPG

Page 475: c 0924494

depurador (continuación)visualización de la ventana de control

de sesión de la depuración 223visualización de registros 223visualización del

almacenamiento 223visualizar variables 223

diferencias de tiempo de ejecuciónjava 280

diseñoaplicación Video Store Catalog 5ayuda en línea 19contenido de la ventana 20lógica del programa 21mensajes 21número de ventanas 20

DLL, archivocarga de la aparición de DLL durante

la depuración 218descripción 413llamada a funciones 256

DSPLY 250

Eedición

archivos de ayuda 212datos en campos de entrada y

componentes texto estático 229, 230fuente RPG 214mensajes 249

editar mensajes de forma directa 251ejecución con puntos de interrupción

programas durante ladepuración 222

puntos de interrupción de ladepuración 221

ejecución de pasos externosdurante la depuración 222

ejecutar subrutinainvocación de subrutinas de acción

con 26ejemplos

actualización de componentescontenedor 66

adición de registros a un componentecontenedor 66

agrupación de botones deselección 136

aplicación Video Store Catalog 3cambio del tamaño de una

ventana 178componente ventana 183de componentes que comparten un

campo de programa 31de transferencia de datos 42eliminación de registros de

componentes contenedor 67lectura y modificación de registros de

subarchivo 154obtención y establecimiento de valores

para componentes selectorcíclico 146

utilización de componente referencia acomponente lógico 62

utilización de subarchivos paravisualizar datos de AS/400 155

ejemplos (continuación)utilización del componente edición de

múltiples líneas 112utilización del componente

graduador 140utilización del componente

imagen 83utilización del componente recuadro

de lista 93utilización del componente subarchivo

de mensajes 108utilización del componente subarchivo

para visualizar registros de base dedatos 156

utilización del componentetemporizador 168

utilización del evento Create para unaventana 38

eliminarcódigo de tiempo de ejecución 407una aplicación 407

empaquetadoaplicación 399código de tiempo de ejecución 399prerrequisitos 399

enlace de componentes 253enlaces de hipertexto, creación 237entradas de posición y conversión

durante la importación 208establecer

fonts de la depuración 227puntos de interrupción de la

depuración 219etiquetas

descripción 39sustitución 247

etiquetas de sustitucióndefinición de texto para 247descripción 39

evento Create, ejemplo de 38evento Enter

para componentes recuadro decombinación 61

para componentes recuadro delista 92, 165

evento GotFocususos comunes de 39y componentes edición de múltiples

líneas 112evento LostFocus, usos comunes de 39evento MenuSelect

para componentes opción demenú 105

evento Presspara componentes pulsador 135para componentes pulsador

gráfico 78evento Select

para componentes botón deselección 138

para componentes recuadro decombinación 61

para componentes recuadro delista 92

para componentes subarchivo 165señalización 56

eventos

Close 182codificación de BEGACT y

ENDACT 26Complete 100comprobación de errores de atributos

de evento 27Change 102, 112, 140descripción de atributos 26Enter 92, 165GotFocus 39, 112invocación de subrutinas de

acción 26listado de eventos para un

componente 26LostFocus 39MenuSelect 105Notify 63para componentes barra de

desplazamiento horizontal 80para componentes barra de

desplazamiento vertical 174para componentes barra de

estado 151para componentes barra de

menús 103para componentes barra de

progreso 133para componentes bean Java 87para componentes botón de

selección 136para componentes campo de

entrada 73para componentes cliente DDE 71para componentes control de

animación 50para componentes cuaderno 115para componentes de ActiveX 47para componentes edición de

múltiples líneas 110para componentes graduador 139para componentes imagen 82para componentes Interfaz

ODBC/JDBC 119para componentes medios 99para componentes opción de

menú 104para componentes página de

cuaderno 116para componentes panel de

medios 101para componentes pulsador 134para componentes pulsador

gráfico 78para componentes recuadro de

combinación 61para componentes recuadro de

contorno 131para componentes recuadro de

grupo 79para componentes recuadro de

lista 90para componentes recuadro de

selección 56para componentes selector

cíclico 145para componentes subarchivo 152

Índice 457

Page 476: c 0924494

eventos (continuación)para componentes subarchivo de

mensajes 106para componentes submenú 166para componentes temporizador 167para componentes texto estático 149para componentes ventana con

lienzo 175, 176Press 78, 135respuesta a eventos en el

programa 26Select 56, 92, 138, 165Tick 167

eventos, atributosdefinición de atributos de evento y de

sistema 28finalidad 26

EXE, archivodescripción 413llamada a archivos .EXE 258

FFirstSel, atributo 59FontName, atributo 149FontSize, atributo 149fuente RPG

reutilizar 214

GGestor de Interfaz de Usuario, reutilizar

archivos 212GETATR

utilización 25GetNewID, atributo 65GetRcdText, atributo 65glosario 437graduador, componente

atributos 139eventos 139finalidad 139

gráfica 75finalidad 75

IICO, archivo

utilización 81, 233iconos, utilización 233imagen, componente

acceso a archivos de imágenes ysonido en tiempo deconstrucción 234

atributos 82especificación del atributo

FileName 233eventos 82finalidad 81

imágenes, adición 233importar 206

archivos de pantalla 206, 207color de componentes

convertidos 211entradas de posición y

conversión 208

importar 206 (continuación)formatos de registro de pantalla 207palabras clave de archivos de

pantalla 209situación 201

iniciarel depurador 217ventana de depuración 217

inicio de componentes lógicosinicio de componentes lógicos 260

inicio de un componente lógico 260InsertItem

para componentes recuadro delista 91

InsertMode, atributo 73instalación

aplicaciones (para Windows NT) 407código de tiempo de ejecución (para

Windows NT) 407código para ejemplos en este

manual 33consideraciones sobre DBCS 363ejemplo Catálogo de vídeos 3

intercambio de información con otrasaplicaciones de PWS 253

IPF (Recurso de Presentación deInformación) 235

Jjava, compilación 277JavaHelp, creación 243Juego de Caracteres de Doble Byte

consideraciones del desarrollo deaplicaciones 363

DBCS puro 365GETATR, código de operación 364,

365SETATR, código de operación 364,

365tipo de datos DBCS cualquiera 363,

365tipo de datos DBCS mixto 363, 365tipo de datos gráficos 365tipo de datos Sólo DBCS 363, 364

Llienzo, componente

atributos 54eventos 54finalidad 53

listas de bibliotecasconfiguración de un servidor 190Consideraciones sobre el cuaderno

Definir información de AS/400 193descripción de trabajo 190QCMDDDM 190, 191QCMDEXC 190

LLllamada a programas locales

funciones locales 256funciones sin parámetros

obligatorios 257

llamada a programas locales(continuación)

funciones utilizando constantes connombre 256

funciones utilizando un puntero deprocedimiento 257

llamada a programas locales 255programas locales 255programas remotos 260

llamada de prototipollamada de prototipo 264

MMasked, atributo 74matriz

modificación durante la sesión dedepuración 224

visualización durante la sesión dedepuración 223

Maximum, atributo 145medios, componente

atributos 99control con el componente panel de

medios 100eventos 99finalidad 99señalización de eventos 100

mensajesbuscar 249compilar para traducir 250crear 247, 248diseñar 21edición 249editar para traducir 251elección del tipo de 248nombrearchivo.TXM 413supresión 249tipos de 247utilización con la lógica 250utilización de etiquetas 251

mensajes de errorerror al referenciar componentes 177salida formateada

incorrectamente 231menú emergente, componente

atributos 132eventos 132finalidad 132

métodos java, invocar 269métodos java, prototipo 270Minimum, atributo 145modificación

eventos de enlace a subrutinas deacción 26

ID de recurso 413MsgSubText, atributo 107

Nnemotécnico

para botones de selección 136para componentes recuadro de

selección 56para elementos de menú 104para páginas del cuaderno 116para pulsadores 134

458 Programación con VisualAge RPG

Page 477: c 0924494

nemotécnico (continuación)traducción 22

Notify, evento 63

Oobtención de la cuenta de registros

atributo de texto para componentes demúltiples líneas 110

atributos de componente 25cuenta de registros en un

subarchivo 154estado de componentes botón de

selección 138estado de componentes recuadro de

selección 55valor para componentes

graduador 139valores para componentes selector

cíclico 146Open Immediately, atributo 176OpenEdit, atributo 155

Ppágina de cuaderno, componente

atributos 116eventos 116finalidad 116

página de cuaderno con lienzo,componente

atributos 117eventos 117finalidad 117

palabras de edicióncorrección de salida formateada

incorrectamente 231cuerpo de 231estado de 232finalidad 229, 230partes de 231posiciones de expansión de 232

panel de medios, componenteatributos 101control del componente medios 100eventos 101finalidad 101

planificación de la aplicación 19posición de los componentes,

cambiar 178proceso recurrente

llamadas recursivas 266programa de lenguaje de control (CL)

ALCOBJ 196CVTRPGSRC, herramienta de

conversión ILE RPG/400 214QCMDDDM 190QCMDEXC 190STRPCCMD 263

programa de utilidad deEmpaquetado 399

programa de utilidad Definir informaciónde AS/400

establecimiento de un servidor entiempo de ejecución 190

y empaquetado de la aplicación 400programas, no GUI 357

programas autónomos 357programas de ejemplo

construir 34ejecutar 34instalar 33instrucciones especiales para ejemplos

que necesiten datos de AS/400 34programas de utilidad

Crear archivo de mensajes 250Definir información de AS/400 190,

400Empaquetado 399

programas no GUI 357Programas no GUI desde DOS 433prototipo, métodos Java 270pseudónimos de archivo (alteraciones

temporales) 192publicaciones, lista de 449pulsador de ayuda, creación 236puntero

modificación del valor durante ladepuración 226

visualización durante ladepuración 225

punto de interrupciónestablecer 219, 221

QQCMDDDM

cambio de la lista de bibliotecas 190QCMDDDM, cambio de la lista de

bibliotecas 190QCMDEXC

cambio de la lista de bibliotecas 190QCMDEXC, cambio de la lista de

bibliotecas 190

RREADC (leer siguiente registro

modificado), código de operación 153READS (leer registro seleccionado del

subarchivo), código de operación 153RecordID, atributo 66recuadro de grupo

atributos 79eventos 79finalidad 79

recuadro de lista, componenteatributos 75, 90eventos 90finalidad 90y transferencia de datos 41

recuadro de selección, componenteatributos 55eventos 55, 56finalidad 55obtención y establecimiento de

estados 55Recurso de Presentación de Información

(IPF) 235referencia

componentes en diferentesventanas 25

componentes en las mismasventanas 25

referencia a componente lógico,componente

atributos 62comunicación entre componentes

lógicos 253ejemplo 62eventos 62finalidad 62

RemoveItem, atributo 59, 91RemoveMsg, atributo 107RemoveRcd, atributo 67RESET

finalidad 30restricciones de java 277reutilización

aplicaciones de AS/400 201archivos de ayuda UIM 212archivos de pantalla 206, 207fuente RPG 214

Sselección de elementos en recuadros de

combinación 59SelectItem, atributo 61selector cíclico, componente

ejemplo de 146eventos 145finalidad 145

servidoresacceso a archivos de base de datos de

AS/400 192acceso a áreas de datos de

AS/400 191alteración de archivos de base de

datos 196bloqueo de archivos de base de

datos 196comprobación de nivel 196configurar para desarrollar/ejecutar

aplicaciones 190consideraciones de base de datos 197consideraciones sobre el

cuaderno 189consideraciones sobre la lista de

bibliotecas 190definición de la información de

AS/400 189emisión de mandatos CL 190llamada a programas AS/400 262llamada a programas AS/400 con

archivos de estación de trabajo 263utilización de la aplicación como

servidor DDE 254SETATR

utilización 25SetRcdIcon, atributo 67SetRcdText, atributo 64, 67SHOWWIN, código de operación

carga de ventana en memoria 177sistema, atributos

comprobación de errores de atributosde sistema 27

sonido, adición 233START (iniciar un componente lógico),

código de operacióndescripción 260

Índice 459

Page 478: c 0924494

START (iniciar un componente lógico),código de operación (continuación)

llamada a programas localesutilizando 259

restricciones al llamar a programaslocales con 260

y componentes referencia acomponente lógico 62

subarchivo, componenteatributos 152campos ocultos 155ejemplo de lectura y actualización de

registros 154ejemplo de visualizar datos de

AS/400 155eventos 152finalidad 152

submenú, componenteatributos 166eventos 166finalidad 166

subrutina de acciónmodificación de eventos de enlace 26

subrutina de acción, invocación 26

Ttemas finales

para componentes graduador 140usos comunes de 37

temporizador, componenteeventos 167finalidad 167

terminación de un programa 182Terminar al cerrar 182texto

finalidad 30para componentes campo de

entrada 73para componentes recuadro de

combinación 59para componentes selector

cíclico 146Tick event 167tiempo de ejecución

actualización 407eliminar 407nombrearchivo.DLL 413nombrearchivo.EXE 413nombrearchivo.HLP 413nombrearchivo.ODX 413nombrearchivo.RST 413suprimir 407volver a empaquetar 407volver a instalar 407

tipo de componentedescripción 264

tipo de datos gráficos 365traducción

compilar mensajes para 250consejos para 22, 40editar mensajes para 251mensajes 22nemotécnico 22

transferencia de datoscomponentes que soportan 41ejemplo 42utilización 41

VValidate, atributo 73valor de color RGB 37valores por omisión

abrir inmediatamente 176contenido de la lista de ventanas 181debido a código de operación

CLEAR 183foco 181orden de los elementos en un

recuadro de combinación 58valores del menú del sistema 182visible 176

varios procedimientosllamada de prototipo 264

ventana con lienzo, componenteatributos 176eventos 176finalidad 176

ventanasatributos 175, 176atributos para códigos de

operación 30cambiar el tamaño 178carga en memoria 177códigos de operación para 30consideraciones sobre el estilo 22creación al iniciar 177cuándo puede establecer

atributos 177dar foco de entrada 38diseño del contenido de 20especificar cuándo visualizar 38establecimiento del contenido de la

lista de ventanas 181establecimiento del foco 181eventos 175, 176finalidad 175, 176método para mover 178nombres exclusivos para componentes

campo de entrada y textoestático 30

OpenImmediately, atributo 176referencia 177situar sin utilizar la barra de

título 178terminación al Cerrar 182utilización de sonido 233valores del menú del sistema 182valores por omisión 176Visible, atributo 176visualización 176visualización de imágenes en 233

View, atributo 70vistas, cambiar 67vistas de contenedor, cambiar 67Visual RPG

barra de herramientas de ladepuración 222

ejecución de puntos deinterrupción 221

establecimiento de fonts de ladepuración 227

establecimiento de puntos deinterrupción 219

información de arranque de ladepuración 219

Visual RPG (continuación)lista de puntos de interrupción 220modificación de un valor de

puntero 226modificación de variables, matrices y

estructuras 224ventana de depuración 217visualización de un valor de

puntero 225visualización de variables, matrices y

estructuras 223visualización del código fuente

ensamblador 218visualización del punto de

interrupción de la carga de laaparición 218

visualizar variablescódigo fuente ensamblador de la

depuración 218punto de interrupción de la carga de

la aparición de la depuración 218valor de puntero durante la

depuración 225variables, matrices y estructuras

durante la depuración 223variables durante la depuración 223

volver a empaquetar 407

WWindows, ayuda, creación 239

460 Programación con VisualAge RPG

Page 479: c 0924494
Page 480: c 0924494

IBM

Número de Programa: 5769-CL3

Printed in Denmark by IBM Danmark A/S

SC10-3067-04