Curso Básico de Programación
en Visual Basic

 

Entrega Cuarenta y siete: 22/Ago/2003
por Guillermo "guille" Som

Si quieres linkar con las otras entregas, desde el índice lo puedes hacer

 

Seguramente pensarás que hay muchas cosas que explicar de Visual Basic, y tienes razón, pero debido a que el título de este "tutorial" es Curso Básico de Programación en Visual Basic, no pretenderás que te lo explique todo... sí, ya sé que eso es lo que "el Guille" debería hacer... pero...
Tampoco te creas que es que quiero "liquidar" ya este curso de Visual Basic... que por ahora no lo voy a dar por terminado, pero... (ya van dos peros), en fin... que tampoco se puede explicar todo... y aunque parezca que no, pero en este curso ya son muchos los conceptos que se han explicado, no todos, lo sé, pero si los suficientes como para que te arriesgues "un poco" e investigues por tu cuenta y riesgo...
No, que no, que no voy a "pasar" del curso básico, simplemente te estoy "medio" advirtiendo que no abarcaré todos los temas, así que... intenta buscar más documentación u otros cursos por Internet y no lo dejes todo de manos del Guille, que no lo vas a tener todo... aunque también te recomiendo que eches un vistazo a las muchas cosas que hay publicadas en mi sitio sobre VB que alguna te servirá... ¡espero!

Bueno, después de este párrafo "liante" vamos a ver que es lo que podemos hacer... o mejor dicho, que es lo que me gustaría explicarte en las entregas que seguirán en un futuro próximo en esto que empieza ahora y que podía ser la segunda parte del Curso Básico de Programación con Visual Basic.

 

Introducción

Lo que me gustaría explicarte son cosas como la creación de controles ActiveX (OCX) y librerías (DLL) ActiveX, que al fin y al cabo son conceptos bastante similares, cuando las explique verás que es así.
También tengo pensado, siguiendo en esta mima línea de "automatización" de Visual Basic, a explicarte cómo modularizar o "trocear" tus aplicaciones en componentes ActiveX, de forma que puedas crear componentes (controles o librerías ActiveX) que sean totalmente funcionales y que puedas usar de forma independiente en distintas aplicaciones.

Para no confundirte mucho, vamos a empezar a repasar algunos "conceptos" de los que hablaremos en esta y próximas entregas, para que cuando te encuentres con esos "términos" no te hagas un lío... (traduzco: no te confundas).

 

Componentes.

Empecemos por explicar qué significa eso de componentes.
Según la documentación de la MSDN Library que se incluye con Visual Studio 6.0 (VB 6.0), un componente es:

Cualquier software compatible con Automatización, por lo que puede usarse mediante programación en una aplicación personalizada. Incluye controles ActiveX, servidores de Automatización basados en Visual Basic y servidores de Automatización basados en Visual C.

Antes de "explicarte" o aclararte que significa esto, veamos lo que dice la documentación sobre Automatización:

Una tecnología que permite que las aplicaciones proporcionen objetos de una forma coherente a otras aplicaciones, herramientas de programación y lenguajes de macros.

Ahora que tenemos definidos dos de los conceptos que aparecen en la documentación de Visual Basic, te explicaré con lenguaje lo más llano posible qué significa esto de los componentes.

Desde la versión 4.0 de Visual Basic, este lenguaje permite crear aplicaciones compatibles con lo que antes se llamaba automatización OLE, (OLE: Object Linking and Embedding, vinculación e incrustación de objetos), ese nombre ahora es más conocido como automatización COM (o simplemente como COM). Las siglas COM significan Component Object Model que traducido sería algo así como modelo de objetos componentes.

Siguiendo mi búsqueda de definiciones en las diferentes "documentaciones" de Microsoft, me he encontrado también con esta otra sobre COM:

COM es el "modelo de objetos" fundamental sobre el que se generan OLE (Object Linking and Embedding, Vinculación e incrustación de objetos) y los controles ActiveX. COM permite que un objeto exponga su funcionalidad a otros componentes y aloje aplicaciones. Define cómo el objeto se expone a sí mismo y cómo funciona dicha exposición en procesos y en redes. Además, COM define el ciclo de vida del objeto.

No es que no quiera explicarte lo que significan todas estas "siglas", es que prefiero que leas lo que la documentación "algunas" veces te dice y después te lo aclaro, para que lo digieras mejor... si es posible.

Lo que debe quedarte claro, es que un componente es un "trozo" de código que podemos usar en cualquier aplicación.
La peculiaridad de los componentes es que son totalmente operativos por sí mismos, te aclaro esto para que no pienses que al decir que es un trozo de código, una rutina (función o procedimiento) podría ser un componente, ya que eso no es totalmente cierto.

Los componentes COM son programas que permiten ser utilizados desde otro programas mediante automatización.
Por regla general, los componentes suelen ser librerías (o si lo prefieres bibliotecas) ActiveX (DLL), controles ActiveX (OCX) e incluso ejecutables ActiveX (EXE).

Nota:
Puede que en esta y siguientes entregas, simplemente utilice la palabra componente, pero cuando lo haga me referiré a componentes de automatización (o componentes COM), ya que en el mundo de .NET también se usa el término componente y su uso no se refiere precisamente a un "objeto" de automatización.

No hace falta que te diga que no es lo mismo un EXE ActiveX que un EXE normal, por la sencilla razón de que si un EXE normal fuese lo mismo... desde hace tiempo que estaríamos creando componentes COM.
Igualmente no es lo mismo una DLL normal que una DLL ActiveX, ya que una DLL "normal" simplemente tiene funciones que podemos usar en nuestras aplicaciones, pero estas se usan directamente, sin la intervención de COM, tal es el caso de las DLLs del API de Windows las cuales podemos usar en cualquier programa. Por otro lado las DLL ActiveX son librerías que se pueden usar sólo con lenguajes que puedan trabajar con Automatización OLE (o COM).

Visual Basic está totalmente "adherido" a la automatización, es decir, entiende cómo crear objetos contenidos en componentes COM (de automatización) y, lo más importante, también puede crear componentes COM para que puedan ser usados desde otros lenguajes "adheridos" a la automatización.

Por tanto, Visual Basic podrá crear librerías (DLL) de automatización (componentes COM), pero no podrá crear librerías "normales".

Aclaro este punto, porque a pesar de que la extensión sea la misma para una librería normal y una de automatización, nuestro querido VB no podrá crear ficheros con la extensión DLL que se puedan usar de la misma forma que las librerías del API de Windows o las creadas por compiladores como C/C++ e incluso Delphi.

Las librerías creadas por Visual Basic siempre son librerías de automatización.

Después de estas aclaraciones, vamos a seguir con las explicaciones de porqué pueden ser útiles estos componentes COM, aunque cuando hable de componentes (o componentes COM) me estaré refiriendo normalmente a "código" que podemos usar desde cualquier aplicación de automatización, y ese "código" normalmente estará compilado en la forma de una librería (DLL).
Realmente no es "código", al menos como se entiende por código cuando se dice "código fuente", sino a código compilado o código binario, es decir, un código fuente que se ha compilado.

 

¿Qué ventajas tiene la creación y utilización de componentes?

Si has llegado a esta entrega número 47, (sin saltarte ninguna), ya habrás estado usando algunos componentes de automatización, por ejemplo ADO (ActiveX Data Objects) es un componente de automatización, el cual nos permite crear objetos para poder acceder a las bases de datos. También habrás usado "componentes" en la forma de librerías del API de Windows. Y por supuesto que habrás usado "componentes" en la forma de controles OCX.
Por tanto la utilidad de usar "componentes" es obvia, si ya hay alguno que nos sirva para nuestra aplicación, lo usamos y no tenemos que programar ni una línea para tener la funcionalidad que ese componente nos ofrece.

Por otro lado, la creación de un componente nos permite escribir un código que "posiblemente" nos servirá para usarlo en más de una aplicación, además de que ese mismo componente podemos distribuirlo para que otros programadores puedan usarlo.
El "posiblemente" lo he entrecomillado, porque si creamos un componente no quiere decir que "forzosamente" tengamos que usarlo en más de una aplicación, ya que es muy posible que simplemente lo usemos una vez y nada más, pero eso no es un impedimento para que lo "encapsulemos" en un componente (librería DLL o control OCX).

¿Cual sería la ventaja de crear un componente aunque sólo nos sirva para una aplicación?
La ventaja es que si en un futuro queremos hacer cambios en el código de ese componente, sólo tendremos que distribuir esa librería y no el resto de la aplicación, incluso (aunque ese tema no lo trataremos en este curso) puede ser que ese componente se ejecute desde un servidor, con lo cual simplemente actualizándolo en el servidor, el resto de las aplicaciones "cliente" que lo utilicen estarán actualizados "a la última".

La ventaja también es evidente, ya que si no tuviésemos el código "troceado", tendríamos que compilar toda la aplicación, de esta forma sólo tendríamos que compilar el componente y distribuirlo... cuando digo distribuirlo, en la mayoría de los casos, simplemente será "copiar y pegar" esa librería en el directorio que estaba y nada más.

Sí, ya se lo que estarás pensando, y si aún no lo estás pensando, este pensamiento te "llegará" cuando sepas algo de la creación de componentes ActiveX, y como no es plan de esperar el tiempo necesario para que sepas algo de componentes, te explico cual sería ese pensamiento al que me refiero:
Pregunta/pensamiento: Si tengo que compilar el componente y distribuirlo, ¿qué problema hay con compilar toda la aplicación y distribuirla?
Respuesta de tu "subconsciente Guille": Pues ninguno. Precisamente por eso te lo "recalco", porque como no hay ninguna diferencia, (salvo que el componente sea uno que resida en un servidor y entonces si que habría diferencia), puedes pensar que ¿para qué complicarme la vida haciendo componentes, cuando es mejor escribir todo el código junto, que con total seguridad me dará menos quebraderos de cabeza? Y si tienes este último pensamiento "pasarás" de crear y usar componentes, y si es eso lo que va a ocurrir... ¿que puñetas, (últimamente el Guille se está volviendo algo más recatado y ahora en lugar de decir coño, dice puñetas, que es casi lo mismo pero suena menos grosero), hago yo aquí tratando de explicarte todo esto?

Pues eso, aunque no los uses, o no pretendas usarlos, empápate de qué va todo esto de los componentes y "aprende" a usarlos aunque pienses que no te será realmente útil. A la larga lo agradecerás, de verdad.
Es como lo de usar Option Explicit, cuando te acostumbras a declarar todas las variables, ya no puedes "vivir" sin declararlas, lo mismo que cuando te acostumbras a indentar el código, si no está indentado, parece que ni lo entiendes... (¡Este Guille no tiene remedio! tenía que aprovechar la coyuntura para darte un par de consejillos de los suyos.)

 

Otra de las cosas que vamos a ir viendo con todo esto de los componentes, serán cosas relacionadas con la programación orientada a objetos, aunque si bien es cierto que el Visual Basic no es un lenguaje orientado a objetos, podemos hacer cosas que "casi" parezcan... por supuesto estoy hablando del Visual Basic 6.0 (y anteriores), ya que el Visual Basic .NET si que es un lenguaje orientado a objetos.

Todo esto es debido a que la creación de componentes ActiveX nos permitirá entrar un "poco" en esa dinámica, por aquello de que la creación de componentes nos permitirá "granular" nuestra aplicación en trozos (que al fin y al cabo serán clases que se convertirán en objetos). Ya se que esto no será Programación Orientada a Objetos, (así en mayúsculas o en negrita), pero al menos te dará una idea de cómo podría ser... y sobre todo, como es ahora mismo si te atreves a entrar en el mundo de .NET, que al fin y al cabo debería ser el lenguaje que deberías usar, así que... no se que haces perdiendo el tiempo en este curso si ya tenías que estar en el de Visual Basic .NET.

Dicho todo esto, quiero que prepares cuerpo y mente para lo que seguirá y, si ves que no estás totalmente preparado, (o preparada), es que va siendo hora de que empieces de nuevo por la entrega uno de este curso, te leas la ayuda del Visual Basic o te dediques a otra cosa, ya que... mejor o peor, (según quien opine), en las 46 entregas anteriores te he explicado un montón de cosas, las cuales, si las has "aderezado" con alguna otra lectura, seguro que te permitirá empezar a adentrarte en el mundillo de la programación con Visual Basic, que al fin y al cabo es lo que este "curso" ha pretendido y pretende.

 

Bueno, ya está bien de charla y vamos a empezar con algo práctico.

 

A la vuelta con las clases.

A partir de la entrega 37 empezamos a tratar el tema de las clases, y en las últimas entregas lo hicimos con más o menos profundidad, espero que con todo lo dicho sobre ese tema, no tengas dudas sobre qué son las clases y cómo se usan en los proyectos de Visual Basic, ya que todo esto de los componentes ActiveX está muy relacionado con las clases y la creación de objetos (instanciación) en la memoria a partir de una clase.


Nota:

Te recomiendo que si el tema de las clases no lo tienes claro, te repases las entregas 37, 38, 39, 39.2, 42, 43, 44, 45 y 46, ya que para poder crear componentes de automatización es fundamental el conocimiento de cómo definir una clase, además de cómo crear nuevas instancias (objetos en memoria) de una clase.
 

 

De todas formas, vamos a repasar rápidamente los conceptos más importantes.

Repaso rápido sobre las clases.

 

 

 

 

 

 

 

 

 

 

 

 

Creo que con este repaso, más o menos, recordarás las cosas más importantes sobre las clases.
De todas formas, algunos de estos conceptos los iremos "repasando" a lo largo de esta y siguientes entregas, incluso puede que aparezcan algunos nuevos y si no nuevos, puede que los explique un poco más a fondo... ya veremos.

 

Para terminar esta entrega, vamos a crear un componente (una librería ActiveX) y veremos cómo podemos "probarla" y usarla desde otros proyectos.

 

Crear un grupo de proyectos.

El entorno de Visual Basic (a partir de la versión 5), nos permite tener múltiples proyectos abiertos.
Esto nos permite poder crear, por ejemplo, un componente, además de poder crear un ejecutable "normal" que nos permita usar ese componente.

Para no complicarte la vida con este primer intento en la creación de un componente, vamos a crear una librería Activex. Esta librería tendrá una clase (como todas las librerías ActiveX) la cual nos permitirá crear un objeto desde una aplicación normal.
Esa clase tendrá dos propiedades: Nombre, Versión (esta última será de solo lectura) y un método: HoraActual.

Aquí veremos, paso a paso, cómo crear este grupo de proyectos, cómo escribir el código de la clase (que como te imaginarás no será nada del otro mundo) y cómo añadir un nuevo proyecto para que podamos probar la librería creada, además de cómo referenciar a esa librería, que como comprobarás, se hace de la misma forma que con el resto de "componentes" COM (o ActiveX).

Empecemos abriendo del Visual Basic, en este ejemplo voy a usar el VB6, si no tienes el VB6, podrás usar el VB5, pero no te servirá el VB5CCE, (ver el apéndice A), ya que el VB5CCE no permite crear librerías DLL ActiveX, lo siento. En otra ocasión veremos cómo crear un control ActiveX y en esa ocasión si podrás usar el VB5CCE.

Cuando nos pregunte el tipo de proyecto a crear, seleccionaremos ActiveX DLL, (ver la figura 1)


Figura 1, Diálogo para crear un nuevo proyecto

 

Se creará un proyecto llamado Project1 (al menos en la versión inglesa de VB6 que es la que tengo instalada)
Ese proyecto tendrá una clase, llamada Class1.
Lo primero que debemos hacer es cambiar el nombre de la clase y del proyecto.
A la clase la vamos a llamar cEntrega47, al proyecto lo llamaremos Entrega47AX.
Es importante que el nombre de la clase y el del proyecto se llamen de forma distinta.
Para poder cambiar el nombre de la clase, selecciona la clase en el Explorador de proyectos y en la ventana de propiedades, escribe el nombre en la propiedad Name (ver figura 2). Si tienes el VB5, habrá menos propiedades mostradas.
Haz lo mismo con el proyecto, selecciona el proyecto en el Explorador de proyectos y cambia la propiedad Name, que será la única que se muestre.


Figura 2, propiedades de la clase

Además de la propiedad Name (nombre) del proyecto, también podemos configurar otras cosas, pero eso lo veremos en otra ocasión.

Ahora vamos a añadirle los "miembros" que tendrá la clase.

Nota:
Aquí voy a usar "las recomendaciones", aunque en este caso podría usar el camino corto por aquello de que es un ejemplo trivial, no quiero que ya desde este momento te vayas acostumbrando a las "malas" formas de programar.

Para crear propiedades, puedes usar el "asistente" del VB, o bien escribir el código directamente.
Si has leído el Apéndice A, en el que te explicaba cómo configurar el entorno del VB, sabrás que me gusta tener en la barra de herramientas un botón (o icono) para crear nuevos procedimientos. Pero si no tienes esa opción en la barra de herramientas, puedes acceder a ella mediante la opción del menú Tools>Add Procedure... (Herramientas>Añadir procedimiento...).
Se mostrará un cuadro de diálogo como el mostrado en la figura 3.


Figura 3, Cuadro para añadir una nueva propiedad a la clase

Y se creará la propiedad con el nombre que hemos indicado, en este caso, la propiedad Nombre. Fíjate que cuando creas una propiedad de esta forma, siempre será del tipo Variant, (ver figura 4), por tanto tendrás que cambiar el tipo para que sea del adecuado, en este caso será del tipo String.


Figura 4, el código creado por Add Procedure...

El código será el siguiente:

'------------------------------------------------------------------------------
' Clase cEntrega47                                                  (22/Ago/03)
' Prueba para el Curso Básico de Visual Basic
'
' ©Guillermo 'guille' Som, 2003
'------------------------------------------------------------------------------
Option Explicit

' las variables privadas que se usarán con las propiedades
Private m_Nombre As String

' La propiedad Nombre
Public Property Get Nombre() As String
    Nombre = m_Nombre
End Property

Public Property Let Nombre(ByVal newValue As String)
    m_Nombre = newValue
End Property

' La propiedad Version será de sólo lectura
Public Property Get Version() As String
    Version = "1.00.0001"
End Property

' El método HoraActual devuelve la fecha y hora actual
Public Function HoraActual() As Date
    HoraActual = Now
End Function

Ahora vamos a añadir un nuevo proyecto, en este caso será del tipo Exe normal.
En el menú  File (Archivo) selecciona Add project... (Añadir proyecto...) se mostrará el cuadro de diálogo mostrado en la figura 5 (que es parecido al de la figura 1), selecciona Standard EXE (recuerda que mi VB está en inglés).


Figura 5, Añadir un nuevo proyecto

Al pulsar en "Open" (Abrir) se creará un nuevo proyecto, el cual se añadirá al Explorador de proyectos (ver figura 6).
Cambia el nombre del proyecto para que tenga el nombre tEntrega47, el nombre del formulario lo vamos a dejar como está, es decir, se llamará Form1.


Figura 6, El explorador de proyectos

Si te fijas, este grupo de proyectos se llamará Group1.
Este nombre puedes cambiarlo cuando lo vayas a grabar o también desde el menú File>Save Group Project As... (Archivo>Guardar Grupo de Proyectos Como...)

Ya tenemos nuestros dos proyectos.
Pero el que los dos proyectos estén "juntos" no quiere decir que el uno sepa del otro. Realmente actuarán como si no se conocieran, es decir, no podremos usar la clase cEntrega47 desde el proyecto de prueba, ya que el proyecto de prueba (tEntrega47) no conoce la existencia de la librería Entrega47AX.

Para que nuestro proyecto de pruebas se entere de la existencia de esa librería, tendremos que añadir una referencia a la misma, (igual que haríamos para añadir una referencia a los objetos de ADO).
Por tanto, tendrás que seleccionar ese proyecto en el Explorador de proyectos y en el menú Project (Proyecto), seleccionar la opción References... (Referencias...) y de las que te muestre, selecciona la que nos interesa, ver figura 7:


Figura 7, Referencias del proyecto EXE de prueba.

A partir de este momento ya podemos crear objetos del tipo cEntrega47, porque el proyecto del ejecutable "sabe" de la existencia del proyecto de la librería. Cosa que podemos comprobar si declaramos, en la ventana de código del formulario, una variable que haga referencia a la clase cEntrega47 (ver figura 8).


Figura 8, Intellisense nos muestra las clases que contiene la librería Entrega47AX

Con ese código mostrado en la figura 8, tenemos una variable que sabe lo que hacer con un objeto del tipo cEntrega47, es decir, que puede tener una referencia a un objeto del tipo cEntrega47.
Para que "realmente" tenga una referencia a un objeto real de la memoria, tendremos que instanciarlo usando New, (como de costumbre), cosa que haremos en el evento Form_Load del formulario, ahora veremos el código, ya que antes vamos a añadir unos controles al formulario para poder probar la clase definida en el componente.
Añade unas etiquetas para que nos muestre la versión y la fecha y hora actual, aunque para que muestre la fecha y hora, tendremos que pulsar en el botón.
El aspecto del formulario en tiempo de diseño será el mostrado en la figura 9:


Figura 9, El formulario en tiempo de diseño

Ahora sólo queda mostrar el código del formulario y probar que todo funciona bien.

Antes de probar que todo funciona bien, veamos el código.

'------------------------------------------------------------------------------
' Formulario de prueba para la clase cEntrega47                     (22/Ago/03)
' Prueba para el Curso Básico de Visual Basic
'
' ©Guillermo 'guille' Som, 2003
'------------------------------------------------------------------------------
Option Explicit

Private prueba47 As Entrega47AX.cEntrega47

Private Sub cmdFechaHora_Click()
    Label4.Caption = prueba47.HoraActual
End Sub

Private Sub Form_Load()
    Set prueba47 = New cEntrega47
    
    Label2.Caption = prueba47.Version
End Sub

Fíjate que la variable declarada a nivel de módulo (en el formulario), se ha declarado como del tipo Entrega47AX.cEntrega47, pero también se podía haber declarado como As cEntrega47, esto no es una característica de nuestro proyecto, sino de todos los componentes ActiveX, ya que no es necesario indicar el "componente" en el que está la clase, salvo que sepamos que puede haber "conflictos de nombres", es decir, dos clases que se llamen de igual forma, pero que estén en distintos componentes, (esto suele ocurrir cuando tenemos referencias a DAO y ADO, en ambos existe un objeto llamado Recordset).
En el Form_Load se instancia (se crea el nuevo objeto) usando el nombre de la clase, sin especificar el del componente, esto no es buena práctica, en este caso te lo muestro para que sepas que los dos cEntrega47 son la misma clase, pero para seguir con las buenas prácticas de programación y, sobre todo, para ser consistentes, deberíamos usar la forma larga o corta, pero no mezclarlas.

Para probar que todo funciona, tendríamos que pulsar F5 o bien en el botón "play" de la barra de herramientas.
Pero como resulta que el primer proyecto que hemos agregado al grupo de proyectos es la librería, se mostrará un cuadro de diálogo preguntándote que quieres ejecutar... es decir, que no se puede ejecutar una librería así por las buenas... por tanto deberíamos indicarle al Visual Basic que el proyecto que queremos probar es el ejecutable.
Para hacer esto, hay que decirle que el proyecto de inicio es tEntrega47, (se mostrará en negrita en el explorador de proyectos), para poder indicar cual será el proyecto de inicio, tenemos que hacerlo usando el menú contextual (pulsa con el botón derecho o secundario del ratón) en el proyecto tEntrega47 y del menú que se muestra, selecciona Set As Start Up (ver la figura 10)


Figura 10, indicar cual será el proyecto de inicio

Una vez que le hemos indicado al VB que el proyecto de inicio es tEntrega47, podemos pulsar F5 y se mostrará el formulario (como en cualquier proyecto "normal"), verás que se muestra la versión de la clase (la que hemos dicho que muestre), y si pulsamos en el botón, se mostrará la fecha y hora actual.

Y esto es todo por hoy.
Espero que, aunque de forma orientativa, ya sepas cómo crear (o al menos probar en el IDE de Visual Basic), un componente ActiveX y lo que es mejor, cómo poder usarlo desde otro proyecto.
Sólo me queda aclararte que como aún no lo hemos compilado, sólo podremos crear referencias si ese otro proyecto, que queremos que use el componente, está en el mismo grupo de proyectos que el del componente.
En otra ocasión veremos cómo compilarlo y cómo configurar la utilización de ese componente, cosa que mucha gente no explica y que puede tener sus más y menos en cuanto a rendimiento... o casi...

Pero eso será en otra ocasión, que ahora me tengo que ir con la parienta, que está algo pachuchilla con un resfriadillo de estos de verano, y cuando las parientas están así, necesitan más cariñete de lo normal...

Nos vemos
Guillermo
 

Este es el código de los dos proyectos de ejemplo: basico47_cod.zip 2.83 KB


 
entrega anterior ir al índice siguiente entrega

Ir al índice principal del Guille