source: 2014/24/EemeliK/Zombieland/Jypeli/AdvanceMath/Design/AdvTypeConverter'.cs @ 5974

Revision 5974, 8.3 KB checked in by empaheik, 4 years ago (diff)
RevLine 
[5974]1#region MIT License
2/*
3 * Copyright (c) 2005-2008 Jonathan Mark Porter. http://physics2d.googlepages.com/
4 *
5 * Permission is hereby granted, free of charge, to any person obtaining a copy
6 * of this software and associated documentation files (the "Software"), to deal
7 * in the Software without restriction, including without limitation the rights to
8 * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
9 * the Software, and to permit persons to whom the Software is furnished to do so,
10 * subject to the following conditions:
11 *
12 * The above copyright notice and this permission notice shall be
13 * included in all copies or substantial portions of the Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
16 * INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
17 * PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
19 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
20 * OTHER DEALINGS IN THE SOFTWARE.
21 */
22#endregion
23
24
25
26using System;
27using System.Collections;
28using System.ComponentModel;
29using System.Reflection;
30#if !CompactFramework && !WindowsCE && !PocketPC && !XBOX360 && !SILVERLIGHT && !WINDOWS_PHONE
31using System.ComponentModel.Design.Serialization;
32#endif
33using System.Globalization;
34
35namespace AdvanceMath.Design
36{
37#if !CompactFramework && !WindowsCE && !PocketPC && !XBOX360 && !SILVERLIGHT && !WINDOWS_PHONE
38    public class AdvTypeConverter<TType> : ExpandableObjectConverter
39    {
40        ConstructorInfo instanceNoArgsCtor;
41        ConstructorInfo instanceCtor;
42        MethodInfo parse;
43        PropertyDescriptorCollection descriptions;
44        string[] instanceCtorParamNames;
45        public AdvTypeConverter()
46        {
47            Type t = typeof(TType);
48            this.parse = ParseMethodAttribute.GetParseMethod(t);
49            this.descriptions = AdvBrowsableAttribute.GetDispMembers(t);
50            if (descriptions != null)
51            {
52                this.instanceNoArgsCtor = t.GetConstructor(Type.EmptyTypes);
53                this.instanceCtor = InstanceConstructorAttribute.GetConstructor(t, out instanceCtorParamNames);
54                if (this.instanceCtor != null)
55                {
56                    ParameterInfo[] paraminfos = instanceCtor.GetParameters();
57                    if (paraminfos.Length == instanceCtorParamNames.Length)
58                    {
59                        for (int index = 0; index < instanceCtorParamNames.Length; ++index)
60                        {
61                            string name = instanceCtorParamNames[index];
62                            PropertyDescriptor descriptor = descriptions.Find(name, false);
63                            if (descriptor == null || descriptor.PropertyType != paraminfos[index].ParameterType)
64                            {
65                                instanceCtor = null;
66                                break;
67                            }
68                        }
69                    }
70                    else
71                    {
72                        instanceCtor = null;
73                    }
74                }
75            }
76        }
77        public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
78        {
79            return 
80                (parse != null && sourceType == typeof(string) )  ||
81                base.CanConvertFrom(context, sourceType);
82        }
83        public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType)
84        {
85            return
86                ((instanceCtor != null || instanceNoArgsCtor != null) &&
87                destinationType == typeof(InstanceDescriptor)) ||
88                base.CanConvertTo(context, destinationType);
89        }
90        public override bool GetCreateInstanceSupported(ITypeDescriptorContext context)
91        {
92            return
93                instanceCtor != null ||
94                instanceNoArgsCtor != null ||
95                base.GetCreateInstanceSupported(context);
96        }
97        public override bool GetPropertiesSupported(ITypeDescriptorContext context)
98        {
99            return
100                descriptions != null ||
101                base.GetPropertiesSupported(context);
102        }
103
104
105
106
107        public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value)
108        {
109            if (parse != null && value is string)
110            {
111                try
112                {
113                    return parse.Invoke(null, new object[] { value });
114                }
115                catch (TargetInvocationException ex)
116                {
117                    throw ex.InnerException;
118                }
119            }
120            return base.ConvertFrom(context, culture, value);
121        }
122        public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType)
123        {
124            if (value is TType &&
125                destinationType == typeof(InstanceDescriptor))
126            {
127                if (instanceCtor != null)
128                {
129                    return new InstanceDescriptor(instanceCtor, GetInstanceDescriptorObjects(value));
130                }
131                else if (instanceNoArgsCtor != null)
132                {
133                    return new InstanceDescriptor(instanceNoArgsCtor, null);
134                }
135            }
136            return base.ConvertTo(context, culture, value, destinationType);
137        }
138
139        public override object CreateInstance(ITypeDescriptorContext context, IDictionary propertyValues)
140        {
141            try
142            {
143                PropertyDescriptor propertyDescriptor = context.Instance as PropertyDescriptor;
144                object result = null;
145                if (instanceNoArgsCtor != null)
146                {
147                    result = instanceNoArgsCtor.Invoke(null);
148                    foreach (string name in propertyValues.Keys)
149                    {
150                        descriptions.Find(name, false).SetValue(result, propertyValues[name]);
151                    }
152                }
153                else if (instanceCtor != null)
154                {
155                    result = instanceCtor.Invoke(GetInstanceDescriptorObjects(propertyValues));
156                }
157                if (result != null)
158                {
159                    if (propertyDescriptor != null)
160                    {
161                        propertyDescriptor.SetValue(null, result);
162                    }
163                    return result;
164                }
165            }
166            catch (TargetInvocationException ex) { throw ex.InnerException; }
167            return base.CreateInstance(context, propertyValues);
168        }
169        public override PropertyDescriptorCollection GetProperties(ITypeDescriptorContext context, object value, Attribute[] attributes)
170        {
171            if (this.descriptions != null)
172            {
173                return this.descriptions;
174            }
175            return base.GetProperties(context, value, attributes);
176        }
177
178        private object[] GetInstanceDescriptorObjects(IDictionary propertyValues)
179        {
180            object[] rv = new object[instanceCtorParamNames.Length];
181            for (int index = 0; index < instanceCtorParamNames.Length; ++index)
182            {
183                rv[index] = propertyValues[descriptions.Find(instanceCtorParamNames[index], false).Name];
184            }
185            return rv;
186        }
187        private object[] GetInstanceDescriptorObjects(object value)
188        {
189            if (value is IDictionary)
190            {
191                return GetInstanceDescriptorObjects((IDictionary)value);
192            }
193            object[] rv = new object[instanceCtorParamNames.Length];
194            for (int index = 0; index < instanceCtorParamNames.Length; ++index)
195            {
196                PropertyDescriptor descriptor = descriptions.Find(instanceCtorParamNames[index], false);
197                rv[index] = descriptor.GetValue(value);
198            }
199            return rv;
200        }
201
202    }
203#endif
204}
Note: See TracBrowser for help on using the repository browser.