The Labs \ Source Viewer \ SSCLI \ System.ComponentModel \ DelegatingTypeDescriptionProvider

  1. //------------------------------------------------------------------------------
  2. // <copyright file="DelegatingTypeDescriptionProvider.cs" company="Microsoft">
  3. //
  4. // Copyright (c) 2006 Microsoft Corporation. All rights reserved.
  5. //
  6. // The use and distribution terms for this software are contained in the file
  7. // named license.txt, which can be found in the root of this distribution.
  8. // By using this software in any fashion, you are agreeing to be bound by the
  9. // terms of this license.
  10. //
  11. // You must not remove this notice, or any other, from this software.
  12. //
  13. // </copyright>
  14. //------------------------------------------------------------------------------
  15. namespace System.ComponentModel
  16. {
  17.     using System;
  18.     using System.Collections;
  19.     using System.Reflection;
  20.     using System.Security.Permissions;
  21.    
  22.     /// <devdoc>
  23.     /// This is a simple type description provider that, when invoked demand
  24.     /// locates the correct type description provider for the given type and
  25.     /// invokes it. This is used as the tail node for both type and instance
  26.     /// based providers. Conceptually it "links" the provider list for one type
  27.     /// or instance to its corresponding base type.
  28.     /// </devdoc>
  29.     [HostProtection(SharedState = true)]
  30.     internal sealed class DelegatingTypeDescriptionProvider : TypeDescriptionProvider
  31.     {
  32.         private Type _type;
  33.        
  34.         /// <devdoc>
  35.         /// Creates a new DelegatingTypeDescriptionProvider. The type is the
  36.         /// type we will delegate to.
  37.         /// </devdoc>
  38.         internal DelegatingTypeDescriptionProvider(Type type)
  39.         {
  40.             _type = type;
  41.         }
  42.        
  43.         /// <devdoc>
  44.         ///
  45.         /// </devdoc>
  46.         private TypeDescriptionProvider Provider {
  47.             get { return TypeDescriptor.GetProviderRecursive(_type); }
  48.         }
  49.        
  50.         /// <devdoc>
  51.         /// This method is used to create an instance that can substitute for another
  52.         /// data type. If the method is not interested in providing a substitute
  53.         /// instance, it should call base.
  54.         /// </devdoc>
  55.         public override object CreateInstance(IServiceProvider provider, Type objectType, Type[] argTypes, object[] args)
  56.         {
  57.             return Provider.CreateInstance(provider, objectType, argTypes, args);
  58.         }
  59.        
  60.         /// <devdoc>
  61.         /// TypeDescriptor may need to perform complex operations on collections of metadata.
  62.         /// Since types are not unloaded for the life of a domain, TypeDescriptor will
  63.         /// automatically cache the results of these operations based on type. There are a
  64.         /// number of operations that use live object instances, however. These operations
  65.         /// cannot be cached within TypeDescriptor because caching them would prevent the
  66.         /// object from garbage collecting. Instead, TypeDescriptor allows for a per-object
  67.         /// cache, accessed as an IDictionary of key/value pairs, to exist on an object.
  68.         /// The GetCache method returns an instance of this cache. GetCache will return
  69.         /// null if there is no supported cache for an object.
  70.         /// </devdoc>
  71.         public override IDictionary GetCache(object instance)
  72.         {
  73.             return Provider.GetCache(instance);
  74.         }
  75.        
  76.         /// <devdoc>
  77.         /// The name of the specified component, or null if the component has no name.
  78.         /// In many cases this will return the same value as GetComponentName. If the
  79.         /// component resides in a nested container or has other nested semantics, it may
  80.         /// return a different fully qualfied name.
  81.         ///
  82.         /// If not overridden, the default implementation of this method will call
  83.         /// GetTypeDescriptor.GetComponentName.
  84.         /// </devdoc>
  85.         public override string GetFullComponentName(object component)
  86.         {
  87.             return Provider.GetFullComponentName(component);
  88.         }
  89.        
  90.         /// <devdoc>
  91.         /// This method returns an extended custom type descriptor for the given object.
  92.         /// An extended type descriptor is a custom type descriptor that offers properties
  93.         /// that other objects have added to this object, but are not actually defined on
  94.         /// the object. For example, in the .NET Framework Component Model, objects that
  95.         /// implement the interface IExtenderProvider can "attach" properties to other
  96.         /// objects that reside in the same logical container. The GetTypeDescriptor
  97.         /// method does not return a type descriptor that provides these extra extended
  98.         /// properties. GetExtendedTypeDescriptor returns the set of these extended
  99.         /// properties. TypeDescriptor will automatically merge the results of these
  100.         /// two property collections. Note that while the .NET Framework component
  101.         /// model only supports extended properties this API can be used for extended
  102.         /// attributes and events as well, if the type description provider supports it.
  103.         /// </devdoc>
  104.         public override ICustomTypeDescriptor GetExtendedTypeDescriptor(object instance)
  105.         {
  106.             return Provider.GetExtendedTypeDescriptor(instance);
  107.         }
  108.        
  109.         /// <devdoc>
  110.         /// The GetReflection method is a lower level version of GetTypeDescriptor.
  111.         /// If no custom type descriptor can be located for an object, GetReflection
  112.         /// is called to perform normal reflection against the object.
  113.         /// </devdoc>
  114.         public override Type GetReflectionType(Type objectType, object instance)
  115.         {
  116.             return Provider.GetReflectionType(objectType, instance);
  117.         }
  118.        
  119.         /// <devdoc>
  120.         /// This method returns a custom type descriptor for the given type / object.
  121.         /// The objectType parameter is always valid, but the instance parameter may
  122.         /// be null if no instance was passed to TypeDescriptor. The method should
  123.         /// return a custom type descriptor for the object. If the method is not
  124.         /// interested in providing type information for the object it should
  125.         /// return null.
  126.         /// </devdoc>
  127.         public override ICustomTypeDescriptor GetTypeDescriptor(Type objectType, object instance)
  128.         {
  129.             return Provider.GetTypeDescriptor(objectType, instance);
  130.         }
  131.     }
  132. }

Developer Fusion