1 // 2 // System.ComponentModel.Design.Serialization.PropertyCodeDomSerializer 3 // 4 // Authors: 5 // Ivan N. Zlatev (contact i-nZ.net) 6 // 7 // (C) 2007 Ivan N. Zlatev 8 9 // 10 // Permission is hereby granted, free of charge, to any person obtaining 11 // a copy of this software and associated documentation files (the 12 // "Software"), to deal in the Software without restriction, including 13 // without limitation the rights to use, copy, modify, merge, publish, 14 // distribute, sublicense, and/or sell copies of the Software, and to 15 // permit persons to whom the Software is furnished to do so, subject to 16 // the following conditions: 17 // 18 // The above copyright notice and this permission notice shall be 19 // included in all copies or substantial portions of the Software. 20 // 21 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 22 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 23 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 24 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 25 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 26 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 27 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 28 // 29 30 31 using System; 32 using System.ComponentModel; 33 using System.ComponentModel.Design; 34 35 using System.CodeDom; 36 37 namespace System.ComponentModel.Design.Serialization 38 { 39 internal class PropertyCodeDomSerializer : MemberCodeDomSerializer 40 { 41 PropertyCodeDomSerializer()42 public PropertyCodeDomSerializer () 43 { 44 } 45 Serialize(IDesignerSerializationManager manager, object value, MemberDescriptor descriptor, CodeStatementCollection statements)46 public override void Serialize (IDesignerSerializationManager manager, object value, MemberDescriptor descriptor, CodeStatementCollection statements) 47 { 48 if (manager == null) 49 throw new ArgumentNullException ("manager"); 50 if (value == null) 51 throw new ArgumentNullException ("value"); 52 if (descriptor == null) 53 throw new ArgumentNullException ("descriptor"); 54 if (statements == null) 55 throw new ArgumentNullException ("statements"); 56 57 PropertyDescriptor property = (PropertyDescriptor) descriptor; 58 59 if (property.Attributes.Contains (DesignerSerializationVisibilityAttribute.Content)) 60 SerializeContentProperty (manager, value, property, statements); 61 else 62 SerializeNormalProperty (manager, value, property, statements); 63 } 64 65 SerializeNormalProperty(IDesignerSerializationManager manager, object instance, PropertyDescriptor descriptor, CodeStatementCollection statements)66 private void SerializeNormalProperty (IDesignerSerializationManager manager, 67 object instance, PropertyDescriptor descriptor, CodeStatementCollection statements) 68 { 69 CodeAssignStatement assignment = new CodeAssignStatement (); 70 71 CodeExpression leftSide = null; 72 CodePropertyReferenceExpression propRef = null; 73 ExpressionContext expression = manager.Context[typeof (ExpressionContext)] as ExpressionContext; 74 RootContext root = manager.Context[typeof (RootContext)] as RootContext; 75 76 if (expression != null && expression.PresetValue == instance && expression.Expression != null) { 77 leftSide = new CodePropertyReferenceExpression (expression.Expression, descriptor.Name); 78 } else if (root != null && root.Value == instance) { 79 leftSide = new CodePropertyReferenceExpression (root.Expression, descriptor.Name); 80 } else { 81 propRef = new CodePropertyReferenceExpression (); 82 propRef.PropertyName = descriptor.Name; 83 propRef.TargetObject = base.SerializeToExpression (manager, instance); 84 leftSide = propRef; 85 } 86 87 CodeExpression rightSide = null; 88 89 MemberRelationship relationship = GetRelationship (manager, instance, descriptor); 90 if (!relationship.IsEmpty) { 91 propRef = new CodePropertyReferenceExpression (); 92 propRef.PropertyName = relationship.Member.Name; 93 propRef.TargetObject = base.SerializeToExpression (manager, relationship.Owner); 94 rightSide = propRef; 95 } else { 96 rightSide = base.SerializeToExpression (manager, descriptor.GetValue (instance)); 97 } 98 99 if (rightSide == null || leftSide == null) { 100 base.ReportError (manager, "Cannot serialize " + ((IComponent)instance).Site.Name + "." + descriptor.Name, 101 "Property Name: " + descriptor.Name + System.Environment.NewLine + 102 "Property Type: " + descriptor.PropertyType.Name + System.Environment.NewLine); 103 } else { 104 assignment.Left = leftSide; 105 assignment.Right = rightSide; 106 statements.Add (assignment); 107 } 108 } 109 SerializeContentProperty(IDesignerSerializationManager manager, object instance, PropertyDescriptor descriptor, CodeStatementCollection statements)110 private void SerializeContentProperty (IDesignerSerializationManager manager, object instance, 111 PropertyDescriptor descriptor, CodeStatementCollection statements) 112 { 113 CodePropertyReferenceExpression propRef = new CodePropertyReferenceExpression (); 114 propRef.PropertyName = descriptor.Name; 115 object propertyValue = descriptor.GetValue (instance); 116 117 ExpressionContext expressionCtx = manager.Context[typeof (ExpressionContext)] as ExpressionContext; 118 if (expressionCtx != null && expressionCtx.PresetValue == instance) 119 propRef.TargetObject = expressionCtx.Expression; 120 else 121 propRef.TargetObject = base.SerializeToExpression (manager, instance); 122 123 CodeDomSerializer serializer = manager.GetSerializer (propertyValue.GetType (), typeof (CodeDomSerializer)) as CodeDomSerializer; 124 if (propRef.TargetObject != null && serializer != null) { 125 manager.Context.Push (new ExpressionContext (propRef, propRef.GetType (), null, propertyValue)); 126 object serialized = serializer.Serialize (manager, propertyValue); 127 manager.Context.Pop (); 128 129 CodeStatementCollection serializedStatements = serialized as CodeStatementCollection; 130 if (serializedStatements != null) 131 statements.AddRange (serializedStatements); 132 133 CodeStatement serializedStatement = serialized as CodeStatement; 134 if (serializedStatement != null) 135 statements.Add (serializedStatement); 136 137 CodeExpression serializedExpr = serialized as CodeExpression; 138 if (serializedExpr != null) 139 statements.Add (new CodeAssignStatement (propRef, serializedExpr)); 140 } 141 } 142 ShouldSerialize(IDesignerSerializationManager manager, object value, MemberDescriptor descriptor)143 public override bool ShouldSerialize (IDesignerSerializationManager manager, object value, MemberDescriptor descriptor) 144 { 145 if (manager == null) 146 throw new ArgumentNullException ("manager"); 147 if (value == null) 148 throw new ArgumentNullException ("value"); 149 if (descriptor == null) 150 throw new ArgumentNullException ("descriptor"); 151 152 PropertyDescriptor property = (PropertyDescriptor) descriptor; 153 154 if (property.Attributes.Contains (DesignOnlyAttribute.Yes)) 155 return false; 156 157 SerializeAbsoluteContext absolute = manager.Context[typeof (SerializeAbsoluteContext)] as SerializeAbsoluteContext; 158 if (absolute != null && absolute.ShouldSerialize (descriptor)) 159 return true; 160 161 bool result = property.ShouldSerializeValue (value); 162 163 if (!result) { 164 if (!GetRelationship (manager, value, descriptor).IsEmpty) 165 result = true; 166 } 167 168 return result; 169 } 170 GetRelationship(IDesignerSerializationManager manager, object value, MemberDescriptor descriptor)171 private MemberRelationship GetRelationship (IDesignerSerializationManager manager, object value, MemberDescriptor descriptor) 172 { 173 MemberRelationshipService service = manager.GetService (typeof (MemberRelationshipService)) as MemberRelationshipService; 174 if (service != null) 175 return service[value, descriptor]; 176 else 177 return MemberRelationship.Empty; 178 } 179 } 180 } 181