En este tema se explica cómo crear y registrar controladores de propiedades para trabajar con el sistema de propiedades de Windows.
Este tema se organiza de la siguiente manera:
Prácticas recomendadas
Invalidar las propiedades del sistema de archivos
El origen de datos del sistema de archivos proporciona algunas propiedades para los archivos, como:
- PKEY_FileName
- PKEY_Extension
- PKEY_ModifiedTime
En general, los controladores de propiedades no pueden proporcionar valores para estas propiedades. Sin embargo, en algunos casos, estas propiedades se pueden invalidar en función de la información de registro proporcionada por el controlador de propiedades. Los controladores de propiedades rellenan HKEY_CLASSES_ROOT\CLSID\{handler clsid}\OverrideFileSystemProperties con los nombres de las propiedades que quieren invalidar. Esto se limita a un conjunto fijo de propiedades que se muestran en la lista siguiente de las que el sistema tiene conocimiento.
La invalidación se admite para los siguientes valores de propiedad:
- System.Kind
- System.FileName
- System.IsPinnedToNameSpaceTree
- System.ItemNameDisplay
- System.SFGAOFlags
- System.ItemPathDisplay
- System.ItemPathDisplayNarrow
- System.ItemFolderNameDisplay
- System.ItemFolderPathDisplay
- System.ItemFolderPathDisplayNarrow
Para obtener una lista completa de todas las propiedades de Shell, consulte Propiedades del shell.
Importante
Los valores de propiedad invalidados solo se usan cuando se indexan los archivos. Por lo tanto, la exploración de archivos desde el origen de datos del sistema de archivos no revela los valores invalidados.
Almacenar propiedades en formatos de archivo basados en XML
Hay dos opciones básicas disponibles para almacenar propiedades en formatos de archivo basados en XML:
- Almacene cada propiedad mediante elementos y atributos XML según el esquema XML del documento. Este enfoque es más descriptivo para XML.
- Serialice todo el almacén de propiedades en un objeto binario grande (BLOB) de memoria, convierta el BLOB en una cadena codificada en base64 y, a continuación, almacene esa cadena en el XML. Este es el más sencillo de los dos enfoques y se puede usar para proporcionar compatibilidad trivial con metadatos abiertos.
Algunos controladores pueden combinar estos enfoques, almacenar algunos valores importantes en formato XML estándar y almacenar el resto en un BLOB, por ejemplo.
Propiedades calculadas
Algunas propiedades se derivan de atributos específicos de un archivo. Por ejemplo, la propiedad System.Image.Dimensions viene determinada por las dimensiones reales de la imagen en un archivo de imagen. Dado que el controlador de propiedades no puede cambiar estos valores de propiedad, se marcan isInnate="true"
así en la descripción de la propiedad. Otras propiedades se calculan desde una parte de una propiedad específica o agregando los valores de varias propiedades. Dado que las actualizaciones de estas propiedades "calculadas" crearían ambigüedad sobre cómo se deben cambiar los valores de "origen", las propiedades calculadas deben marcarse isInnate="true"
en la descripción de la propiedad o notificarse como de solo lectura. Esta última opción está disponible al indicar al controlador que devuelva S_FALSE desde IPropertyStoreCapabilities::IsPropertyWritable.
Preguntas más frecuentes
¿Por qué el indexador de Windows Search no carga mi controlador de propiedades?
El indexador de Windows Search se ejecuta como un servicio del sistema y no puede cargar archivos DLL almacenados en el directorio del perfil de usuario. Si va a compilar y depurar con Microsoft Visual Studio, colocará el archivo DLL en el perfil de usuario (y, por lo tanto, el indexador no cargará). Para solucionarlo, copie el archivo DLL fuera de la carpeta de perfil (por ejemplo, en C:\Archivos de programa\YourAppName) y regístrelo allí.
Para obtener instrucciones más específicas sobre el desarrollo de controladores de propiedades para trabajar con el indexador de Windows Search, consulta Developing Property Handlers for Windows Search.
¿Qué propiedades se deben detectar mediante los métodos de enumeración "IPropertyStore::GetCount" y "IPropertyStore::GetAt"?
No todos los clientes de objetos de almacén de propiedades usan estos métodos. Algunos clientes conocen las propiedades que planean solicitar directamente (por nombre PKEY) o recibir información de propiedad a través de una lista de descripción de propiedades. Los métodos de detección de propiedades ofrecen otros escenarios. Si no es necesario que una propiedad participe en estos escenarios, no es necesario enumerar. Por lo tanto, un controlador de propiedades puede generar un valor que no sea VT_EMPTY para las propiedades que no se detectan a través de los métodos IPropertyStore::GetCount e IPropertyStore::GetAt .
Sin embargo, las propiedades deben ser visibles a través de estos métodos si se cumple alguna de las condiciones siguientes:
-
Si la propiedad está indizada para que se pueda buscar: Esto significa que se incluye en el almacén de propiedades de Windows Search (indicado por
isColumn = "true"
en el esquema de descripción de la propiedad) o disponible para búsquedas de texto completo (inInvertedIndex = "true"
). En ausencia de estas marcas o la ausencia de una descripción de propiedad, las propiedades del tipo "string" se agregarán automáticamente al índice invertido para habilitar la búsqueda. Dado que la lista de propiedades conocidas (aquellas con descripciones de propiedades instaladas) en el sistema de propiedades es muy grande (más de 800 propiedades), sería poco práctico pedir a cada controlador de propiedades para cada propiedad registrada en el sistema de propiedades. En su lugar, el proceso de indexación enumera las propiedades pertinentes del controlador de propiedades para cada elemento que indexa y usa los valores de las propiedades enumeradas para compilar el índice de texto completo. - Si la propiedad debe copiarse cuando se duplica el conjunto de propiedades del elemento: Para implementar una función "copiar un conjunto de propiedades", el elemento de origen hace que las propiedades que se deben copiar sean visibles a través de los métodos IPropertyStore::GetCount e IPropertyStore::GetAt . Las propiedades que no necesitan copiarse o no tienen sentido que se copien no deben incluirse.
- Si el valor de la propiedad no está vacío (VT_EMPTY): Los valores de propiedad que están vacíos no son útiles para los clientes. Cuando los clientes intentan devolver valores de propiedad vacíos, se devuelve un valor de VT_EMPTY. Por lo tanto, no se deben enumerar las propiedades con valores vacíos.
- Si se debe quitar la propiedad al invocar la función "remove properties": Esta característica existe para proteger la privacidad; detecta todos los valores del controlador de propiedades a través de la enumeración y quita cada uno seleccionado para su eliminación por parte del usuario.
Nota
La enumeración de propiedades no comunica el conjunto de propiedades que admite un controlador de propiedades determinado si el controlador admite un esquema fijo (y no metadatos abiertos). En su lugar, estos controladores deben documentar el conjunto de propiedades que admiten.
Cómo saber qué formatos de archivo admiten metadatos abiertos?
Para obtener información sobre la compatibilidad con metadatos abiertos, vea "Tipos de archivo que admiten metadatos abiertos" en Tipos de archivo.
¿Se pueden almacenar VT_NULL valores mediante un controlador de propiedades?
No. VT_NULL valores se convertirán en VT_EMPTY en llamadas a IPropertyStore::GetValue e IPropertyStore::SetValue.
¿Qué formatos de cadena de fecha son compatibles con la función 'PropVariantChangeType'?
Por lo general, las propiedades que representan valores de fecha y hora deben representarse mediante VT_FILETIME. Sin embargo, muchos orígenes de datos proporcionan esta información en forma de cadena. La API auxiliar PropVariantChangeType admite la coercción de algunos formatos de fecha de cadena en valores FILETIME , como se muestra en la tabla siguiente.
Formato | Windows Vista, Windows XP y Microsoft Windows Desktop Search (WDS) | Windows 7 | Notas |
---|---|---|---|
aaaa/mm/dd:hh:mm:ss.uuu | Sí | Sí | UTC; y=year, m=month, d=date, h=hours (reloj de 24 horas), m=minutes, s=seconds, u=microsegundos |
aaaa-mm-ddThh:mm:ssZ | No | Sí |
Especificación de formato ISO8601 UTC (indicado por el indicador de zona horaria "Z"); y=year, m=month, d=date, h=hours (reloj de 24 horas), m=minutes, s=seconds; 'T' es un delimitador para la parte de tiempo. |
¿Es posible crear un controlador de propiedades de solo lectura?
Sí. Algunas implementaciones del controlador de propiedades no admiten la escritura de valores de propiedad. Estos controladores de propiedades deben devolver STGM_E_ACCESSDENIED en llamadas a IInitializeXXX::Initialize que pasen STGM_READWRITE o en cualquier llamada a IPropertyStore::SetValue.
Todos los controladores de propiedades abiertos en modo STGM_READ deben devolver STGM_E_ACCESSDENIED en llamadas a IPropertyStore::SetValue.
¿Un controlador de propiedades puede tratar una propiedad como de solo lectura, incluso si el esquema indica que la propiedad es grabable?
Sí. En el sistema de esquema, las propiedades se anotan como de solo lectura (incluidas las con isInnate = "true"
) o de lectura y escritura. Los controladores de propiedades que no admiten la escritura de una propiedad determinada que dice que el esquema debe ser grabable deben implementar IPropertyStoreCapabilities y devolver S_FALSE en llamadas a IPropertyStoreCapabilities::IsPropertyWritable para esa propiedad. Esto indica que, en el contexto de este controlador y este archivo, la propiedad no se puede escribir.
Nota
La acción inversa no es posible. No se puede habilitar un controlador de propiedades para escribir una propiedad marcada como de solo lectura en el esquema.