Está en la página 1de 10

Borland C++ Builder. MLTIPLES VENTANAS.

Fundamentos de Programacin (Ciclo superior A.S.I.)

Borland C++ Builder. Apndice III. USO DE MTIPLES VENTANAS. Los ejemplos que se han propuesto hasta ahora han sido tan simples que estaban compuestos de tan slo un formulario. En la prctica, la mayora de los programas se sirven de mltiples ventanas. Por regla general siempre existe una ventana principal, en la que se encuentra el men de opciones, y una serie de ventanas accesorias que pueden estar visibles siempre o slo cuando sean necesarias. Un programa puede utilizar mltiples ventanas simplemente para solicitar una determinada informacin, como puede ser el nombre del archivo que se desea abrir, o bien para facilitar la edicin de mltiples documentos. Las ventanas del primer tipo se suelen construir como cuadros de dilogo, nombre con el que se conoce a aquellas ventanas que no pueden ser redimensionadas, no cuentan con botones de maximizar o minimizar y que adems son modales, no permitiendo seguir trabajando con la aplicacin hasta que no sean cerradas. En el caso de que el programa sea capaz de permitir el trabajo con mltiples documentos de forma simultnea, stos pueden ser mostrados en ventanas totalmente independientes o bien en una interfaz de documento mltiple, que se conoce como MDI. Cuando una aplicacin cuenta con varios formularios es normal hacer referencia a unos desde otros. Para poder hacer referencia a un formulario desde un mdulo de cdigo que no es el suyo, debemos aadir una directiva include facilitando el nombre del fichero de cabecera correspondiente al mdulo en el que est definido el formulario al que queremos acceder. La forma ms fcil es usar la opcin Include Unit Hdr del men File. En un proyecto tan slo puede existir un formulario principal, que es el que se muestra inicialmente cuando se ejecuta el programa. Cualquiera de los formularios de nuestra aplicacin puede ser el formulario principal. Para establecerlo deberemos usar la opcin Options del men Project, que da lugar a la siguiente ventana:

Juana Snchez Rey 2002/2003

Borland C++ Builder. MLTIPLES VENTANAS.

Fundamentos de Programacin (Ciclo superior A.S.I.)

En esta ventana se define cul es el formulario principal, cuales son formularios autocreados y cules estarn disponibles. En el ejemplo, Form1 es el formulario principal, Form2 es un formulario autocreado, es decir, que podemos usarlo en cualquier momento sin ocuparnos de ningn trabajo de preparacin, y Form3 es un formulario disponible, por lo que no se crea inicialmente, sino que el programa slo cuenta con una plantilla o definicin de sus caractersticas. Para poder usar este ltimo formulario tendremos que crearlo y liberar la memoria ocupada por l cuando deje de sernos til. Creacin de un formulario disponible La creacin de un formulario disponible se realiza mediante el operador new y un constructor: un mtodo especial que se encarga de asignar la memoria necesaria y llevar a cabo todo el proceso de inicializacin preciso. Este constructor se llama igual que la clase y necesita como nico parmetro una referencia a un componente, que ser el dueo del formulario que se est creando. Lo habitual es usar como parmetro el objeto this, que es un puntero al propio formulario desde el que se est creando.
TForm3 * Formulario = new TForm3(this);

A partir de este momento podemos referenciar el nuevo formulario mediante el nombre que le hemos dado, por ejemplo:
Formulario->Caption=Soy el tercer formulario; Formulario->Show();

Destruccin de un formulario Cuando el formulario ha sido creado automticamente por el cdigo del propio proyecto no tenemos que preocuparnos por su destruccin. Sin embargo, cuando el formulario lo hemos creado nosotros mismos, deberemos destruirlo liberando la memoria ocupada por ste. Para ello se utiliza la funcin delete(). delete(Formulario); Si lo que queremos es que el formulario se libere automticamente cuando el usuario lo cierre podemos usar el evento OnClose, asignando al parmetro Action el valor caFree. Visualizacin de un formulario Un formulario cuenta con los mtodos Show(), que lo hace visible y Hide(), que lo oculta. Tambin podemos acceder directamente a la propiedad Visible, asignndole el valor true o false. Un formulario que se muestra por estos mtodos es una ventana no modal, lo que significa que el usuario puede acceder a otras ventanas del mismo programa sin necesidad de cerrar sta. Este es el tipo lgico de visualizacin cuando la ventana va a servir para mostrar informacin. Sin embargo, si la ventana modifica en algn aspecto el entorno del programa no debera permitirse el acceso al resto de las funciones hasta en tanto el formulario no sea cerrado. Para conseguir esto bastar mostrarlo mediante el mtodo ShowModal().
Juana Snchez Rey 2002/2003

Borland C++ Builder. MLTIPLES VENTANAS.

Fundamentos de Programacin (Ciclo superior A.S.I.)

Formularios MDI Cada vez que se aade un nuevo formulario con la opcin New Form, el formulario creado tiene el estilo normal o por defecto, representado por la constante fsNormal. Este estilo de formulario es el de una ventana independiente, que no acta como contenedor de otras ventanas ni est contenido dentro de ninguna y que, adems, puede ser ocultada total o parcialmente por otras ventanas. La propiedad FormStyle es la que determina el estilo del formulario. Si la propiedad toma el valor fsStayOnTop, la ventana siempre se visualizar sobre las dems, no siendo posible ocultarla. Los otros dos estilos permitidos son fsMDIForm y fsMDIChild, cuya finalidad es permitir la creacin de aplicaciones MDI (Multiple Document Interface / Interfaz de Documento Mltiple). El trmino hace referencia a un tipo de aplicacin compuesta por una ventana principal, a la que denominamos padre, capaz de contener en su interior mltiples ventanas a las que se denominan hijas. La ventana que acta como padre tiene el estilo fsMDIForm y cada ventana hija tendr el estilo fsMDIChild. La finalidad de la interfaz MDI (interfaz de documentos mltiples) es facilitar la edicin simultnea de varios documentos. En una interfaz MDI existe una ventana principal o marco, que es la que cuenta con el men de opciones, la barra de botones, la lnea de estado, etc y una o ms ventanas hija. Las ventanas hija MDI siempre se visualizan en el interior de la ventana marco, no pudiendo extenderse ms all de ella. Aquellos formularios que van a actuar como ventanas hija debern ser definidos como formularios disponibles y no como formularios autocreados. La ventana principal cuenta con una serie de propiedades y mtodos que facilitan la gestin de las ventanas hija. La propiedad MDIChildCount contiene el nmero de ventanas hijas existentes, mientras que ActiveMDIChild almacena una referencia a la ventana hija que en ese momento tiene el foco de entrada. Mediante los mtodos Cascade() y Tile() podemos disponer las ventanas hijas existentes en ese momento solapadas o en forma de mosaico, mientras que el mtodo ArrangeIcons() nos permite ordenar las ventanas que en ese momento estn minimizadas.

EN LA PRCTICA
Con el fin de ver en la prctica cmo podemos utilizar mltiples formularios en un proyecto y algunos de los cuadros de dilogo que nos aporta Windows, vamos a disear un programa que nos permita editar ficheros de texto, con la posibilidad de tener abiertos varios de ellos de forma simultnea en un entorno MDI. El texto de cada ventana estar contenido en un control TMemo, por lo que no es posible el uso de atributos de texto. Sin embargo, cada ventana puede tener un tipo de letra y color diferentes al resto.
Juana Snchez Rey 2002/2003

Borland C++ Builder. MLTIPLES VENTANAS.

Fundamentos de Programacin (Ciclo superior A.S.I.)

Diseo del formulario principal El formulario principal del proyecto actuar como ventana marco de la interfaz MDI. Este formulario ser el que existe inicialmente en el proyecto, al que vamos a darle el ttulo Multi Editor. Deber tener el valor fsMDIForm en la propiedad FormStyle. Se insertar un men de opciones desde el cual ser posible abrir un fichero, guardarlo, crear nuevos ficheros, modificar el tipo de letra y el color de fondo y gestionar las mltiples ventanas hija que puedan existir. El men de opciones (componente TMainMenu) deber tener las siguientes opciones:

Juana Snchez Rey 2002/2003

Borland C++ Builder. MLTIPLES VENTANAS.

Fundamentos de Programacin (Ciclo superior A.S.I.)

Para permitir las diferentes opciones que se deducen de las opciones del men, tendremos que insertar un componente TSaveDialog, un TOpenDialog, un TFontDialog y un TColorDialog. El formulario quedar en tiempo de diseo tal y como se muestra a continuacin:

Se asignar a la propiedad Title del componente TSaveDialog la cadena Guardar fichero de texto, y a la misma propiedad del componente TOpenDialog la cadena Abrir fichero de texto. A la propiedad Filter de ambos componentes abr
Juana Snchez Rey 2002/2003

Borland C++ Builder. MLTIPLES VENTANAS.

Fundamentos de Programacin (Ciclo superior A.S.I.)

que asignar Ficheros de Texto | *.txt. Tambin abr que activar del componente TSaveDialog las opciones ofOverwritePrompt y ofPathMustExist, y en el componente TOpenDialog la propiedad ofFileMustExist. Diseo del formulario hijo El siguiente paso es aadir al proyecto un nuevo formulario, para lo que pulsaremos el botn New Form. Este formulario actuar como hijo y en ejecucin podrn existir mltiples copias de l abiertas. Por ello esta ventana no deber ser creada automticamente, sino que habr que especificar que est slo disponible.

Como este nuevo formulario va a ser una ventana hija habr que darle el valor fsMDIChild a su propiedad FormStyle. Para visualizar y permitir la edicin del texto insertaremos en este formulario un campo TMemo que ocupar todo el espacio disponible en la ventana (Align=alClient), que contar con una barra de desplazamiento vertical (ScrollBars=ssVertical) y que permitir la introduccin del tabulador (WantTabs=true). El cdigo del formulario principal Mediante la opcin Include Unit Hdr del men File aadiremos al primer formulario una referencia al segundo, lo que nos permitir acceder a la definicin de TForm2.

Juana Snchez Rey 2002/2003

Borland C++ Builder. MLTIPLES VENTANAS.

Fundamentos de Programacin (Ciclo superior A.S.I.)

El ttulo de cada ventana hija se establecer en ejecucin. En caso de que la ventana se cree abrindose un fichero existente el ttulo ser el nombre de ste. Si, por el contrario, la ventana se ha creado vaca, asignaremos como ttulo la palabra Nuevo seguida de un nmero que se ir incrementando secuencialmente. Este contador se declarar en la parte private de la definicin del formulario, que se encuentra en el fichero de cabecera correspondiente:

Para crear un nuevo fichero, la opcin Nuevo del men Archivo tendr que ser pulsada. Por tanto habr que seleccionar esta opcin para abrir el editor de cdigo por el mtodo correspondiente y escribir lo siguiente:
void __fastcall TForm1::Nuevo1Click(TObject *Sender) {
Juana Snchez Rey 2002/2003

Borland C++ Builder. MLTIPLES VENTANAS.

Fundamentos de Programacin (Ciclo superior A.S.I.)

TForm2 * Formulario = new TForm2(this); Contador++; Formulario->Caption="Nuevo"+AnsiString(Contador);

La opcin Guardar del men Archivo no debe estar accesible en caso de que no exista ninguna ventana hija abierta. Para ello deberemos hacer click en el man Archivo para abrir el mtodo correspondiente al evento OnClick. En este caso asignaremos a la propiedad Enabled de la opcin Guardar los valores true o false, dependiendo de que exista o no un formulario hijo activo en ese momento:
void __fastcall TForm1::Archivo1Click(TObject *Sender) { Guardar1->Enabled=ActiveMDIChild != NULL; }

Si la opcin Guardar est activa y la seleccionamos, tendremos que solicitar un nombre de fichero, para lo que se uar el componente TSaveDialog. A continuacin obtendremos una referencia a la ventana hija que est activa en ese momento, mediante la propiedad ActiveMDIChild, realizando la necesaria conversin al tipo TForm2. Esto nos permitir acceder al control TMemo y realizar una llamada al mtodo SaveToFile(). A continuacin asignaremos a la propiedad Caption del formulario el nombre del archivo seleccionado y daremos el valor false a la propiedad Modified de TMemo, indicando que no se ha modificado desde la ltima grabacin. El mtodo completo sera:
void __fastcall TForm1::Guardar1Click(TObject *Sender) { if (SaveDialog1->Execute()) { TForm2 * FormularioActivo = static_cast<TForm2 *>(ActiveMDIChild); try { FormularioActivo->Memo1->Lines->SaveToFile(SaveDialog1->FileName); FormularioActivo->Caption=SaveDialog1->FileName; FormularioActivo->Memo1->Modified=false; } catch(...) {ShowMessage("Se produce error al guardar");} } }

La opcin Recuperar es la complementaria a la anterior. Mediante ella podemos abrir una ventana con el contenido de un archivo ya existente. Tras solicitar el nombre del fichero, crearemos una nueva ventana hija a accederemos a su control TMemo para recuperar el fichero. Asignaremos el ttulo de la ventana, daremos el valor false a la propiedad Modified y mostraremos la nueva ventana hija. El cdigo correspondiente a su evento OnClick ser el siguiente:
void __fastcall TForm1::Recuperar1Click(TObject *Sender) { if (OpenDialog1->Execute()) { TForm2 * Formulario = new TForm2(this); try {
Juana Snchez Rey 2002/2003

Borland C++ Builder. MLTIPLES VENTANAS.

Fundamentos de Programacin (Ciclo superior A.S.I.)

Formulario->Memo1->Lines->LoadFromFile(OpenDialog1->FileName); Formulario->Caption=OpenDialog1->FileName; Formulario->Memo1->Modified=false; Formulario->Show(); } catch(...) {ShowMessage("Se produce error al recuperar");} }

La opcin Salir tendr como finalidad cerrar la aplicacin. Para ello bastar llamar al mtodo Close() de la forma:
void __fastcall TForm1::Salir1Click(TObject *Sender) { Close(); }

La primera opcin del men Estilo es Letra, una opcin que nos permitir seleccionar cualquier tipo, tamao y estilo de letra para mostrar el texto de la ventana que en ese momento est activa. Para ello obtendremos los valores actuales de la propiedad Font del control TMemo, asignndolos a la propiedad Font del control TFontDialog. Mostraremos el cuadro de dilogo y si se ha pulsado el botn Aceptar, realizaremos la asignacin contraria.
void __fastcall TForm1::Letra1Click(TObject *Sender) { TForm2 * FormularioActivo = static_cast<TForm2 *>(ActiveMDIChild); FontDialog1->Font=FormularioActivo->Memo1->Font; if (FontDialog1->Execute()) FormularioActivo->Memo1->Font=FontDialog1->Font; }

Del mismo modo, el cdigo asociado a la opcin Color ser el siguiente:


void __fastcall TForm1::Color1Click(TObject *Sender) { TForm2 * FormularioActivo = static_cast<TForm2 *>(ActiveMDIChild); ColorDialog1->Color=FormularioActivo->Memo1->Color; if (ColorDialog1->Execute()) FormularioActivo->Memo1->Color=ColorDialog1->Color; }

Por ltimo encontramos en el men una opcin Ventana conteniendo tres opciones que nos permiten disponer las ventanas hija en forma de cascada, en forma de mosaico o bien organizar los iconos de aquellas ventanas que estn minimizadas. Los cdigos asociados sern los siguientes:
void __fastcall TForm1::Cascada1Click(TObject *Sender) { Cascade(); } void __fastcall TForm1::Mosaico1Click(TObject *Sender) { Tile();
Juana Snchez Rey 2002/2003

Borland C++ Builder. MLTIPLES VENTANAS.

Fundamentos de Programacin (Ciclo superior A.S.I.)

} void __fastcall TForm1::OrganizarIconos1Click(TObject *Sender) { ArrangeIcons(); }

El cdigo del formulario hijo Mediante la opcin Include Unit Hdr del men File aadiremos al segundo formulario una referencia al formulario principal mediante la opcin Include Unit Hdr. Como hemos podido ver en el punto anterior, los mtodos que se encargan de guardar y recuperar el texto de una ventana activa utilizan la propiedad Modified del control TMemo para indicar que no se han realizado modificaciones. Esta propiedad tomar automticamente el valor true en el momento en que el usuario modifique el texto. Por lo tanto, en el momento en que se desee cerrar una ventana habr que comprobar esta propiedad y actuar en consecuencia. Para poder hacer esto escribiremos el cdigo siguiente correspondiente al evento OnCloseQuery.
void __fastcall TForm2::FormCloseQuery(TObject *Sender, bool &CanClose) { if (Memo1->Modified) switch(Application->MessageBox("Desea guardar los cambios?",("Cerrar"+Caption).c_str(),MB_YESNOCANCEL)) { case ID_YES: Form1->Guardar1Click(this); break; case ID_CANCEL: CanClose=false; } }

Cuando se pulsa el botn de cierre de una ventana hija MDI lo que ocurre es que sta se minimiza, pero no se destruye, por lo que habr que liberar la memoria usada por la ventana segn lo siguiente:
void __fastcall TForm2::FormClose(TObject *Sender, TCloseAction &Action) { Action=caFree; }

Ya slo bastara probar el programa. Esto es to, esto es to, esto es todo, amigos!!

Juana Snchez Rey 2002/2003

10

También podría gustarte