Controles ActiveX MFC: Temas avanzados
Este artículo cubre temas avanzados relacionados con desarrollar controles ActiveX. Se incluyen los siguientes:
Utilizar clases de base de datos en Controles ActiveX
Implementar una propiedad de Parametrizada
Controlar errores en el control ActiveX se
Administrar claves especial en el Control
El diálogo de acceso controla Que invisible en tiempo de ejecución
Utilizar clases de base de datos en Controles ActiveX
Dado que las clases de control ActiveX forman parte de la biblioteca de clases, puede solicitar los mismos procedimientos y reglas utilizar clases de base de datos en una aplicación estándar de MFC a desarrollar controles ActiveX que utilizan las clases de base de datos MFC.
Para obtener información general sobre de las clases de base de datos de MFC, vea Clases de base de datos MFC (DAO y ODBC). El caso presenta las clases ODBC de MFC y las clases DAO de MFC y guía a más detalles en.
Nota
A partir de Visual C++ .NET, el entorno y los asistentes de Visual C++ ya no admiten DAO (aunque las clases DAO están incluidas y todavía puede utilizarlas).Microsoft recomienda utilizar Plantillas OLE DB o ODBC y MFC para nuevos proyectos.Sólo debería utilizar DAO para mantener las aplicaciones existentes.
Implementar una propiedad de Parametrizada
Una propiedad con parámetros (denominada en ocasiones una matriz de propiedades) es un método para exponer una colección homogénea de valores como una propiedad del control. Por ejemplo, puede utilizar una propiedad con parámetros para exponer una matriz o un diccionario como una propiedad. En Visual Basic, esta propiedad se usa la notación de matrices:
x = o.Array(2, 3) ' gets element of 2D array
o.Array(2, 3) = 7 ' sets element of 2D array
Utilice el asistente para agregar propiedades para implementar una propiedad parametrizada. El asistente para agregar implementa la propiedad agregando un par de funciones Get/set que permiten al usuario del control tenga acceso a la propiedad mediante la notación anterior o en modo estándar.
Similar a los métodos y propiedades, propiedades parametrizadas también tienen un límite al número de parámetros permitidos. En el caso de propiedades parametrizadas, el límite es 15 parámetros (con un parámetro reservado para almacenar el valor de propiedad).
El procedimiento siguiente se agrega una propiedad con parámetros, denominada Array, que puede tener acceso como matriz de enteros bidimensional.
Para agregar una propiedad con parámetros mediante el asistente para agregar propiedades
Cargue el proyecto de control.
En la vista de clases, expanda el nodo de biblioteca de controles.
Haga clic con el botón secundario en el nodo de la interfaz del control (el segundo nodo el nodo de biblioteca) para abrir el menú contextual.
En el menú contextual, haga clic en Add y haga clic en Agregar propiedad.
En el cuadro de Nombre de propiedad , Arrayescrito.
En el cuadro de Tipo de propiedad , seleccione corto.
Para el tipo de Implementación , haga clic en Get/Set Methods.
En los cuadros de Get Function y de Establecer función , nombres únicos escritos para las funciones get y set o aceptan los nombres predeterminados.
Agregue un parámetro, denominado row (tipo short), utilizando los controles de Nombre del parámetro y de Tipo de parámetro .
Agregue column denominado segundo parámetro (tipo short).
Haga clic en Finalizar.
Cambios realizados por el asistente para agregar propiedades
Cuando se agrega una propiedad personalizada, el asistente para agregar realiza cambios en el encabezado de la clase control (. H) y los archivos de implementación (.CPP).
Las líneas siguientes se agregan a la clase de control. Archivo de h:
SHORT GetArray(SHORT row, SHORT column);
void SetArray(SHORT row, SHORT column, SHORT newVal);
Este código declara dos funciones llamadas GetArray y SetArray que permiten al usuario solicitar una fila y una columna específicas para tener acceso a la propiedad.
Además, el asistente para agregar agregue las líneas siguientes al mapa de envío del control, ubicado en el archivo de implementación de la clase control (.CPP):
DISP_PROPERTY_PARAM_ID(CMyAxUICtrl, "Array", dispidArray, GetArray, SetArray, VT_I2, VTS_I2 VTS_I2)
Finalmente, las implementaciones de GetArray y las funciones de SetArray se agregan al final del archivo de .CPP. En la mayoría de los casos, modificará la función get para devolver el valor de la propiedad. La función determinada contendrá normalmente el código que debe ejecutarse, antes o después de que la propiedad cambia.
Para que esta propiedad sea útil, puede declarar una variable miembro de la matriz bidimensional en la clase de control, de cortotipo, los valores almacenados para la propiedad parametrizada. A continuación modificar la función get para devolver el valor almacenado en la fila y la columna adecuadas, como se indica en los parámetros, y modifica la función determinada para actualizar el valor hace referencia a los parámetros de fila y columna.
Controlar errores en el control ActiveX se
Si las condiciones de error aparecen en el control, puede ser necesario notificar el error al contenedor del control. Hay dos métodos para notificar errores, dependiendo de la situación en la que el error. Si el error se produce dentro de una propiedad obtiene o establece la función, o dentro de la implementación de un método de automatización OLE, el control debe llamar a COleControl::ThrowError, que señala al usuario del control que se ha producido un error a. Si el error se produce en otro momento, el control debe llamar a COleControl::FireError, que activa un evento Error común.
Para indicar el tipo de error que se ha producido, el control debe pasar un código de error a ThrowError o a FireError. Un código de error es un código de estado OLE, que tiene un valor de 32 bits. Cuando sea posible, elija un código de error del conjunto estándar de códigos definidos en el archivo de encabezado de OLECTL.H. La tabla siguiente se resumen estos códigos.
Códigos de error de controles ActiveX
Error |
Descripción |
---|---|
CTL_E_ILLEGALFUNCTIONCALL |
Llamada ilegal a una función |
CTL_E_OVERFLOW |
Desbordamiento |
CTL_E_OUTOFMEMORY |
Memoria insuficiente |
CTL_E_DIVISIONBYZERO |
División por cero |
CTL_E_OUTOFSTRINGSPACE |
Sin espacio de cadena |
CTL_E_OUTOFSTACKSPACE |
Sin espacio de pila |
CTL_E_BADFILENAMEORNUMBER |
Nombre de archivo incorrecto o número |
CTL_E_FILENOTFOUND |
Archivo no encontrado |
CTL_E_BADFILEMODE |
Modo de archivo incorrecto |
CTL_E_FILEALREADYOPEN |
Archivo abierto |
CTL_E_DEVICEIOERROR |
Error de E/S de dispositivo |
CTL_E_FILEALREADYEXISTS |
El archivo ya existe |
CTL_E_BADRECORDLENGTH |
Longitud de registro errónea |
CTL_E_DISKFULL |
Disco lleno |
CTL_E_BADRECORDNUMBER |
Número de registros de error |
CTL_E_BADFILENAME |
Nombre de archivo incorrecto |
CTL_E_TOOMANYFILES |
Demasiados archivos |
CTL_E_DEVICEUNAVAILABLE |
Dispositivo no disponibles |
CTL_E_PERMISSIONDENIED |
Permiso denegado |
CTL_E_DISKNOTREADY |
Disco no está listo |
CTL_E_PATHFILEACCESSERROR |
Ruta/al archivo |
CTL_E_PATHNOTFOUND |
Ruta no encontrada |
CTL_E_INVALIDPATTERNSTRING |
Cadena no válida del modelo |
CTL_E_INVALIDUSEOFNULL |
Uso no válido de NULL |
CTL_E_INVALIDFILEFORMAT |
Formato de archivo no válido |
CTL_E_INVALIDPROPERTYVALUE |
Valor de propiedad no válido |
CTL_E_INVALIDPROPERTYARRAYINDEX |
Índice no válido de la matriz de propiedades |
CTL_E_SETNOTSUPPORTEDATRUNTIME |
Conjunto no compatible en tiempo de ejecución |
CTL_E_SETNOTSUPPORTED |
Conjunto no compatible (propiedad de sólo lectura) |
CTL_E_NEEDPROPERTYARRAYINDEX |
Índice de la matriz de propiedades de la necesidad |
CTL_E_SETNOTPERMITTED |
Conjunto no permitido |
CTL_E_GETNOTSUPPORTEDATRUNTIME |
Obtenga no compatible en tiempo de ejecución |
CTL_E_GETNOTSUPPORTED |
Obtenga no compatible (la propiedad de sólo escritura) |
CTL_E_PROPERTYNOTFOUND |
Propiedad no encontrada |
CTL_E_INVALIDCLIPBOARDFORMAT |
Formato no válido del portapapeles |
CTL_E_INVALIDPICTURE |
Imagen no válida |
CTL_E_PRINTERERROR |
Error de impresora |
CTL_E_CANTSAVEFILETOTEMP |
No puede guardar el archivo en TEMP |
CTL_E_SEARCHTEXTNOTFOUND |
Busque el texto no encontrado |
CTL_E_REPLACEMENTSTOOLONG |
Reemplazos demasiado largo |
Si es necesario, utilice la macro de CUSTOM_CTL_SCODE para definir un código de error personalizado para una condición que no está cubierto por uno de los códigos estándar. El parámetro para esta macro debe ser un entero entre 1000 y 32767, ambos inclusive. Por ejemplo:
#define MYCTL_E_SPECIALERROR CUSTOM_CTL_SCODE(1000)
Si está creando un control ActiveX para reemplazar un control existente de VBX, defina los códigos de error de control ActiveX con los mismos valores numéricos que el control de VBX utiliza para garantizar que los códigos de error son compatibles.
Administrar claves especial en el Control
Puede que en algunos casos para controlar ciertas combinaciones de presiones de tecla de una manera especial; por ejemplo, inserte una nueva línea cuando la tecla ENTRAR se clava un control o un movimiento de cuadro de texto de varias líneas entre un grupo de controles de edición cuando un Id. de clave direccional presionó.
Si la clase base de controles ActiveX es COleControl, puede reemplazar CWnd::PreTranslateMessage para controlar los mensajes antes de que el contenedor los procese. Con esta técnica, VERDADERO siempre return si controla el mensaje en la invalidación de PreTranslateMessage.
El ejemplo de código siguiente se muestra una manera de administrar cualquier mensaje relacionado con teclas direccionales.
BOOL CMyAxUICtrl::PreTranslateMessage(MSG* pMsg)
{
BOOL bHandleNow = FALSE;
switch (pMsg->message)
{
case WM_KEYDOWN:
switch (pMsg->wParam)
{
case VK_UP:
case VK_DOWN:
case VK_LEFT:
case VK_RIGHT:
bHandleNow = TRUE;
break;
}
if (bHandleNow)
{
OnKeyDown((UINT)pMsg->wParam, LOWORD(pMsg->lParam), HIWORD(pMsg->lParam));
}
break;
}
return bHandleNow;
}
Para obtener más información sobre cómo administrar las interfaces de teclado para un control ActiveX, vea la documentación de ActiveX SDK.
Controles de acceso de diálogo ese invisible en tiempo de ejecución
Puede crear controles de cuadro de diálogo que no tienen interfaz de usuario y no son visibles en tiempo de ejecución. Si agrega un no visible en el control ActiveX en tiempo de ejecución a un cuadro de diálogo y utiliza CWnd::GetDlgItem para tener acceso al control, el control no funcionará correctamente. En su lugar, debe usar una de las técnicas siguientes para obtener un objeto que representa el control:
Mediante el asistente para agregar variables miembro, Control Variable seleccione y seleccione el identificador de control Escriba un nombre de variable miembro y seleccione la clase contenedora de control como Tipo de control.
O bien
Declare una variable local y conviértala subclases como elemento de diálogo. Inserte el código similar al siguiente (CMyCtrl es la clase contenedora, IDC_MYCTRL1 es el identificador del control):
CCirc myCirc; myCirc.SubclassDlgItem(IDC_CIRCCTRL2, this); // ... use myCirc ... myCirc.UnsubclassWindow();