[tests] Separate MONO_PATH directories by PLATFORM_PATH_SEPARATOR
[mono.git] / mcs / class / System.Web / System.Web.UI.WebControls / ImageField.cs
1 //
2 // System.Web.UI.WebControls.ImageField.cs
3 //
4 // Authors:
5 //      Lluis Sanchez Gual (lluis@novell.com)
6 //
7 // (C) 2005-2010 Novell, Inc (http://www.novell.com)
8 //
9
10 //
11 // Permission is hereby granted, free of charge, to any person obtaining
12 // a copy of this software and associated documentation files (the
13 // "Software"), to deal in the Software without restriction, including
14 // without limitation the rights to use, copy, modify, merge, publish,
15 // distribute, sublicense, and/or sell copies of the Software, and to
16 // permit persons to whom the Software is furnished to do so, subject to
17 // the following conditions:
18 // 
19 // The above copyright notice and this permission notice shall be
20 // included in all copies or substantial portions of the Software.
21 // 
22 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
23 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
24 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
25 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
26 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
27 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
28 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 //
30
31 using System.Collections;
32 using System.Collections.Specialized;
33 using System.Web.UI;
34 using System.ComponentModel;
35 using System.Security.Permissions;
36 using System.Reflection;
37
38 namespace System.Web.UI.WebControls {
39
40         [AspNetHostingPermissionAttribute (SecurityAction.LinkDemand, Level = AspNetHostingPermissionLevel.Minimal)]
41         [AspNetHostingPermissionAttribute (SecurityAction.InheritanceDemand, Level = AspNetHostingPermissionLevel.Minimal)]
42         public class ImageField : DataControlField
43         {
44                 public static readonly string ThisExpression = "!";
45                 
46                 PropertyDescriptor imageProperty;
47                 PropertyDescriptor textProperty;
48                 
49                 public override bool Initialize (bool sortingEnabled, Control control)
50                 {
51                         return base.Initialize (sortingEnabled, control);
52                 }
53
54                 [DefaultValueAttribute ("")]
55                 [LocalizableAttribute (true)]
56                 [WebSysDescription ("")]
57                 [WebCategoryAttribute ("Appearance")]
58                 public virtual string AlternateText {
59                         get {
60                                 object ob = ViewState ["AlternateText"];
61                                 if (ob != null)
62                                         return (string) ob;
63                                 return String.Empty;
64                         }
65                         set {
66                                 ViewState ["AlternateText"] = value;
67                                 OnFieldChanged ();
68                         }
69                 }
70
71                 [DefaultValueAttribute (true)]
72                 [WebSysDescription ("")]
73                 [WebCategoryAttribute ("Behavior")]
74                 public virtual bool ConvertEmptyStringToNull {
75                         get {
76                                 object ob = ViewState ["ConvertEmptyStringToNull"];
77                                 if (ob != null)
78                                         return (bool) ob;
79                                 return true;
80                         }
81                         set {
82                                 ViewState ["ConvertEmptyStringToNull"] = value;
83                                 OnFieldChanged ();
84                         }
85                 }
86
87                 [TypeConverterAttribute ("System.Web.UI.Design.DataSourceViewSchemaConverter, " + Consts.AssemblySystem_Design)]
88                 [DefaultValueAttribute ("")]
89                 [WebSysDescription ("")]
90                 [WebCategoryAttribute ("Data")]
91                 public virtual string DataAlternateTextField {
92                         get {
93                                 object ob = ViewState ["DataAlternateTextField"];
94                                 if (ob != null)
95                                         return (string) ob;
96                                 return String.Empty;
97                         }
98                         set {
99                                 ViewState ["DataAlternateTextField"] = value;
100                                 OnFieldChanged ();
101                         }
102                 }
103
104                 [DefaultValueAttribute ("")]
105                 [WebSysDescription ("")]
106                 [WebCategoryAttribute ("Data")]
107                 public virtual string DataAlternateTextFormatString {
108                         get {
109                                 object ob = ViewState ["DataAlternateTextFormatString"];
110                                 if (ob != null)
111                                         return (string) ob;
112                                 return String.Empty;
113                         }
114                         set {
115                                 ViewState ["DataAlternateTextFormatString"] = value;
116                                 OnFieldChanged ();
117                         }
118                 }
119
120                 [TypeConverterAttribute ("System.Web.UI.Design.DataSourceViewSchemaConverter, " + Consts.AssemblySystem_Design)]
121                 [DefaultValueAttribute ("")]
122                 [WebSysDescription ("")]
123                 [WebCategoryAttribute ("Data")]
124                 public virtual string DataImageUrlField {
125                         get {
126                                 object ob = ViewState ["DataImageUrlField"];
127                                 if (ob != null)
128                                         return (string) ob;
129                                 return String.Empty;
130                         }
131                         set {
132                                 ViewState ["DataImageUrlField"] = value;
133                                 OnFieldChanged ();
134                         }
135                 }
136
137                 [DefaultValueAttribute ("")]
138                 [WebSysDescription ("")]
139                 [WebCategoryAttribute ("Data")]
140                 public virtual string DataImageUrlFormatString {
141                         get {
142                                 object ob = ViewState ["DataImageUrlFormatString"];
143                                 if (ob != null)
144                                         return (string) ob;
145                                 return String.Empty;
146                         }
147                         set {
148                                 ViewState ["DataImageUrlFormatString"] = value;
149                                 OnFieldChanged ();
150                         }
151                 }
152
153                 [DefaultValueAttribute ("")]
154                 [LocalizableAttribute (true)]
155                 [WebSysDescription ("")]
156                 [WebCategoryAttribute ("Behavior")]
157                 public virtual string NullDisplayText {
158                         get {
159                                 object ob = ViewState ["NullDisplayText"];
160                                 if (ob != null) return (string) ob;
161                                 return "";
162                         }
163                         set {
164                                 ViewState ["NullDisplayText"] = value;
165                                 OnFieldChanged ();
166                         }
167                 }
168
169                 [DefaultValueAttribute ("")]
170                 [EditorAttribute ("System.Web.UI.Design.ImageUrlEditor, " + Consts.AssemblySystem_Design, "System.Drawing.Design.UITypeEditor, " + Consts.AssemblySystem_Drawing)]
171                 [UrlPropertyAttribute]
172                 [WebSysDescription ("")]
173                 [WebCategoryAttribute ("Behavior")]
174                 public virtual string NullImageUrl {
175                         get {
176                                 object ob = ViewState ["NullImageUrl"];
177                                 if (ob != null)
178                                         return (string) ob;
179                                 return String.Empty;
180                         }
181                         set {
182                                 ViewState ["NullImageUrl"] = value;
183                                 OnFieldChanged ();
184                         }
185                 }
186
187                 [DefaultValueAttribute (false)]
188                 [WebSysDescription ("")]
189                 [WebCategoryAttribute ("Behavior")]
190                 public virtual bool ReadOnly {
191                         get {
192                                 object val = ViewState ["ReadOnly"];
193                                 return val != null ? (bool) val : false;
194                         }
195                         set { 
196                                 ViewState ["ReadOnly"] = value;
197                                 OnFieldChanged ();
198                         }
199                 }
200
201                 public override void ExtractValuesFromCell (IOrderedDictionary dictionary, DataControlFieldCell cell, DataControlRowState rowState, bool includeReadOnly)
202                 {
203                         if ((ReadOnly && !includeReadOnly) || cell.Controls.Count == 0)
204                                 return;
205                         
206                         bool editable = (rowState & (DataControlRowState.Edit | DataControlRowState.Insert)) != 0;
207                         if (includeReadOnly || editable) {
208                                 Control control = cell.Controls [0];
209                                 //TODO: other controls?
210                                 if (control is Image)
211                                         dictionary [DataImageUrlField] = ((Image)control).ImageUrl;
212                                 else if (control is TextBox)
213                                         dictionary [DataImageUrlField] = ((TextBox) control).Text;
214                         }
215                 }
216                 
217                 public override void InitializeCell (DataControlFieldCell cell, DataControlCellType cellType, DataControlRowState rowState, int rowIndex)
218                 {
219                         base.InitializeCell (cell, cellType, rowState, rowIndex);
220                         if (cellType == DataControlCellType.DataCell) {
221                                 InitializeDataCell (cell, rowState);
222                                 if ((rowState & DataControlRowState.Insert) == 0)
223                                         cell.DataBinding += new EventHandler (OnDataBindField);
224                         }
225                 }
226                 
227                 protected virtual void InitializeDataCell (DataControlFieldCell cell, DataControlRowState rowState)
228                 {
229                         bool editable = (rowState & (DataControlRowState.Edit | DataControlRowState.Insert)) != 0;
230                         if (editable && !ReadOnly) {
231                                 TextBox box = new TextBox ();
232                                 cell.Controls.Add (box);
233                         } else if (DataImageUrlField.Length > 0) {
234                                 Image img = new Image ();
235                                 img.ControlStyle.CopyFrom (ControlStyle);
236                                 cell.Controls.Add (img);
237                         }
238                 }
239                 
240                 protected virtual string FormatImageUrlValue (object value)
241                 {
242                         if (value == null)
243                                 return null;
244                         else if (DataImageUrlFormatString.Length > 0)
245                                 return string.Format (DataImageUrlFormatString, value);
246                         else
247                                 return value.ToString ();
248                 }
249                 
250                 protected virtual string GetFormattedAlternateText (Control controlContainer)
251                 {
252                         if (DataAlternateTextField.Length > 0) {
253                                 if (textProperty == null)
254                                         textProperty = GetProperty (controlContainer, DataAlternateTextField);
255                                         
256                                 object value = GetValue (controlContainer, DataAlternateTextField, ref textProperty);
257                                 
258                                 if (value == null || (value.ToString().Length == 0 && ConvertEmptyStringToNull))
259                                         return NullDisplayText;
260                                 else if (DataAlternateTextFormatString.Length > 0)
261                                         return string.Format (DataAlternateTextFormatString, value);
262                                 else
263                                         return value.ToString ();
264                         } else
265                                 return AlternateText;
266                 
267                 }
268                 
269                 protected virtual object GetValue (Control controlContainer, string fieldName, ref PropertyDescriptor cachedDescriptor)
270                 {
271                         if (DesignMode)
272                                 return GetDesignTimeValue ();
273                         else {
274                                 object dataItem = DataBinder.GetDataItem (controlContainer);
275                                 if (dataItem == null)
276                                         throw new HttpException ("A data item was not found in the container. The container must either implement IDataItemContainer, or have a property named DataItem.");
277                                 if (fieldName == ThisExpression)
278                                         return dataItem;
279                                 else {
280                                         if (cachedDescriptor != null) return cachedDescriptor.GetValue (dataItem);
281                                         PropertyDescriptor prop = GetProperty (controlContainer, fieldName);
282                                         return prop.GetValue (dataItem);
283                                 }
284                         }
285                 }
286                 
287                 PropertyDescriptor GetProperty (Control controlContainer, string fieldName)
288                 {
289                         if (fieldName == ThisExpression)
290                                 return null;
291                         
292                         IDataItemContainer dic = (IDataItemContainer) controlContainer;
293                         PropertyDescriptorCollection properties = TypeDescriptor.GetProperties (dic.DataItem);
294                         PropertyDescriptor prop = properties != null ? properties [fieldName] : null;
295                         if (prop == null)
296                                 throw new InvalidOperationException ("Property '" + fieldName + "' not found in object of type " + dic.DataItem.GetType());
297                         
298                         return prop;
299                 }
300                 
301                 protected virtual string GetDesignTimeValue ()
302                 {
303                         return "Databound";
304                 }
305                 
306                 protected virtual void OnDataBindField (object sender, EventArgs e)
307                 {
308                         Control control = (Control) sender;
309                         ControlCollection controls = control != null ? control.Controls : null;
310                         Control namingContainer = control.NamingContainer;
311                         Control c;
312                         if (sender is DataControlFieldCell) {
313                                 if (controls.Count == 0)
314                                         return;
315                                 c = controls [0];
316                         } else if (sender is Image || sender is TextBox)
317                                 c = control;
318                         else
319                                 return;
320
321                         if (imageProperty == null)
322                                 imageProperty = GetProperty (namingContainer, DataImageUrlField);
323                         
324                         if (c is TextBox) {
325                                 object val = GetValue (namingContainer, DataImageUrlField, ref imageProperty);
326                                 ((TextBox)c).Text = val != null ? val.ToString() : String.Empty;
327                         } else if (c is Image) {
328                                 Image img = (Image)c;
329                                 string value =  FormatImageUrlValue (GetValue (namingContainer, DataImageUrlField, ref imageProperty));
330                                 if (value == null || (ConvertEmptyStringToNull && value.Length == 0)) {
331                                         if (NullImageUrl == null || NullImageUrl.Length == 0) {
332                                                 c.Visible = false;
333                                                 Label label = new Label ();
334                                                 label.Text = NullDisplayText;
335                                                 controls.Add (label);
336                                         } else
337                                                 value = NullImageUrl;
338                                 }
339                                 img.ImageUrl = value;
340                                 img.AlternateText = GetFormattedAlternateText (namingContainer);
341                         }
342                 }
343                 
344                 public override void ValidateSupportsCallback ()
345                 {
346                 }
347                 
348                 protected override DataControlField CreateField ()
349                 {
350                         return new ImageField ();
351                 }
352                 
353                 protected override void CopyProperties (DataControlField newField)
354                 {
355                         base.CopyProperties (newField);
356                         ImageField field = (ImageField) newField;
357                         field.AlternateText = AlternateText;
358                         field.ConvertEmptyStringToNull = ConvertEmptyStringToNull;
359                         field.DataAlternateTextField = DataAlternateTextField;
360                         field.DataAlternateTextFormatString = DataAlternateTextFormatString;
361                         field.DataImageUrlField = DataImageUrlField;
362                         field.DataImageUrlFormatString = DataImageUrlFormatString;
363                         field.NullDisplayText = NullDisplayText;
364                         field.NullImageUrl = NullImageUrl;
365                         field.ReadOnly = ReadOnly;
366                 }
367         }
368 }