New test.
[mono.git] / mcs / class / System.Web / System.Web / SiteMapNode.cs
1 //
2 // System.Web.SiteMapNode
3 //
4 // Authors:
5 //      Ben Maurer (bmaurer@users.sourceforge.net)
6 //
7 // (C) 2003 Ben Maurer
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 #if NET_2_0
32 using System.Collections;
33 using System.Collections.Specialized;
34 using System.Text;
35 using System.Web.UI;
36 using System.Web.UI.WebControls;
37 using System.ComponentModel;
38
39 namespace System.Web {
40         public class SiteMapNode : IHierarchyData, INavigateUIData, ICloneable {
41         
42                 private SiteMapNode () {}
43                 
44                 public SiteMapNode (SiteMapProvider provider, string key) : this (provider, key, null, null, null, null, null, null, null) {}
45                 public SiteMapNode (SiteMapProvider provider, string key, string url) : this (provider, key, url, null, null, null, null, null, null) {}
46                 public SiteMapNode (SiteMapProvider provider, string key, string url, string title) : this (provider, key, url, title, null, null, null, null, null) {}
47                 public SiteMapNode (SiteMapProvider provider, string key, string url, string title, string description) : this (provider, key, url, title, description, null, null, null, null) {}
48                 public SiteMapNode (SiteMapProvider provider, string key, string url, string title, string description, IList roles, NameValueCollection attributes, NameValueCollection explicitResourceKeys, string implicitResourceKey)
49                 {
50                         if (provider == null)
51                                 throw new ArgumentNullException ("provider");
52                         if (key == null)
53                                 throw new ArgumentNullException ("key");
54                         
55                         this.provider = provider;
56                         this.key = key;
57                         this.url = url;
58                         this.title = title;
59                         this.description = description;
60                         this.roles = roles;
61                         this.attributes = attributes;
62                         this.resourceKeys = explicitResourceKeys;
63                         this.implicitResourceKey = implicitResourceKey;
64                 }
65
66                 public SiteMapDataSourceView GetDataSourceView (SiteMapDataSource owner, string viewName)
67                 {
68                         return new SiteMapDataSourceView (owner, viewName, this);
69                 }
70                 
71                 public SiteMapHierarchicalDataSourceView GetHierarchicalDataSourceView ()
72                 {
73                         return new SiteMapHierarchicalDataSourceView (this);
74                 }
75                 
76                 public virtual bool IsAccessibleToUser (System.Web.HttpContext ctx)
77                 {
78                         return provider.IsAccessibleToUser (ctx, this);
79                 }
80                 
81                 public override string ToString()
82                 {
83                         return Title;
84                 }
85
86                 public virtual bool HasChildNodes {
87                         get { return ChildNodes != null && ChildNodes.Count != 0; }
88                 }
89
90                 public SiteMapNodeCollection GetAllNodes ()
91                 {
92                         SiteMapNodeCollection ret;
93                 
94                         ret = new SiteMapNodeCollection ();
95                         GetAllNodesRecursive (ret);
96                         return SiteMapNodeCollection.ReadOnly (ret);
97                 }
98                 
99                 void GetAllNodesRecursive(SiteMapNodeCollection c)
100                 {
101                         SiteMapNodeCollection childNodes = this.ChildNodes;
102                         
103                         if (childNodes.Count > 0) {
104                                 childNodes.AddRange (childNodes);
105                                 foreach (SiteMapNode n in childNodes)
106                                         n.GetAllNodesRecursive (c);
107                         }
108                 }
109
110                 
111                 public virtual bool IsDescendantOf (SiteMapNode node)
112                 {
113                         for (SiteMapNode n = ParentNode; n != null; n = n.ParentNode)
114                                 if (n == node) return true; 
115
116                         return false; 
117                 }
118                 
119                 public virtual SiteMapNode NextSibling {
120                         get {
121                                 IList siblings = this.SiblingNodes;
122                                 if (siblings == null)
123                                         return null; 
124                                 
125                                 int pos = siblings.IndexOf (this);
126                                 if (pos >= 0 && pos < siblings.Count - 1)
127                                         return (SiteMapNode) siblings [pos + 1]; 
128                                 
129                                 return null; 
130                         }
131                 }
132                 
133                 public virtual SiteMapNode PreviousSibling {
134                         get {
135                                 IList siblings = this.SiblingNodes;
136                                 if (siblings == null)
137                                         return null; 
138                                 
139                                 int pos = siblings.IndexOf (this);
140                                 if (pos > 0 && pos < siblings.Count)
141                                         return (SiteMapNode) siblings [pos - 1]; 
142                                 
143                                 return null; 
144                         }
145                 }
146                 
147                 public virtual SiteMapNode ParentNode {
148                         get {
149                                 if (parent != null) return parent;
150                                 
151                                 SiteMapProvider provider = this.provider;
152                                 
153                                 do {
154                                         parent = provider.GetParentNode (this);
155                                         if (parent != null)
156                                                 return parent; 
157                                         
158                                         provider = provider.ParentProvider;
159                                 } while (provider != null);
160                                 return null;
161                         }
162                         set {
163                                 CheckWritable ();
164                                 parent = value;
165                         }
166                 }
167                 
168                 public virtual SiteMapNodeCollection ChildNodes {
169                         get {
170                                 if (childNodes != null) return childNodes;
171                                 return provider.GetChildNodes (this);
172                         } 
173                         set {
174                                 CheckWritable ();
175                                 childNodes = value;
176                         }
177                 }
178
179                 public virtual SiteMapNode RootNode { get { return provider.RootProvider.RootNode; }  }
180                 
181                 SiteMapNodeCollection SiblingNodes {
182                         get {
183                                 if (ParentNode != null)
184                                         return ParentNode.ChildNodes;
185                                 
186                                 return null;
187                         }
188                 }
189                 
190                 [MonoTODO]
191                 protected string GetExplicitResourceString (string attributeName, string defaultValue, bool throwIfNotFound)
192                 {
193                         return null;
194                 }
195                 
196                 [MonoTODO]
197                 protected string GetImplicitResourceString (string attributeName)
198                 {
199                         return null;
200                 }
201                 
202                 [MonoTODO ("resource string?")]
203                 public virtual string this [string key]
204                 {
205                         get {
206                                 string val = null;
207                                 if (provider.EnableLocalization) {
208                                         val = GetExplicitResourceString (key, null, true);
209                                         if (val == null) val = GetImplicitResourceString (key);
210                                 }
211                                 if (val != null) return null;
212                                 if (attributes != null) return attributes [key];
213                                 return null;
214                         }
215                         set {
216                                 CheckWritable ();
217                                 if (attributes == null) attributes = new NameValueCollection ();
218                                 attributes [key] = value;
219                         }
220                 }
221                 
222                 object ICloneable.Clone ()
223                 {
224                         return Clone (false);
225                 }
226                 
227                 public virtual SiteMapNode Clone ()
228                 {
229                         return Clone (false);
230                 }
231                 
232                 public virtual SiteMapNode Clone (bool cloneParentNodes)
233                 {
234                         SiteMapNode node = new SiteMapNode ();
235                         node.provider = provider;
236                         node.key = key;
237                         node.url = url;
238                         node.title = title;
239                         node.description = description;
240                         if (roles != null)
241                                 node.roles = new ArrayList (roles);
242                         if (attributes != null)
243                                 node.attributes = new NameValueCollection (attributes);
244                         if (cloneParentNodes && ParentNode != null)
245                                 node.parent = (SiteMapNode) ParentNode.Clone (true);
246                         return node;
247                 }
248                                 
249                 public override bool Equals (object ob)
250                 {
251                         SiteMapNode node = ob as SiteMapNode;
252                         if (node == null) return false;
253                         
254                         if (node.key != key ||
255                                         node.url != url ||
256                                         node.title != title ||
257                                         node.description != description) {
258                                 return false;
259                         }
260
261                         if (roles == null || node.roles == null) {
262                                 if (roles != node.roles)
263                                         return false;
264                         }
265                         else {
266                                 if (roles.Count != node.roles.Count)
267                                         return false;
268
269                                 foreach (object role in roles)
270                                         if (!node.roles.Contains (role)) return false;
271                         }
272                         if (attributes == null || node.attributes == null) {
273                                 if (attributes != node.attributes)
274                                         return false;
275                         }
276                         else {
277                                 if (attributes.Count != node.attributes.Count)
278                                         return false;
279
280                                 foreach (string k in attributes)
281                                         if (attributes[k] != node.attributes[k])
282                                                 return false;
283                         }
284                         return true;
285                 }
286                 
287                 public override int GetHashCode ()
288                 {
289                         return (key + url + title + description).GetHashCode ();
290                 }
291                 
292                 void CheckWritable ()
293                 {
294                         if (readOnly)
295                                 throw new InvalidOperationException ("Can't modify read-only node");
296                 }
297                                 
298                 #region Field Accessors
299                 
300                 protected NameValueCollection Attributes {
301                         get { return attributes; } 
302                         set { CheckWritable (); attributes = value; }
303                 }
304                 
305                 [Localizable (true)]
306                 public virtual string Description {
307                         get { return description != null ? description : ""; }
308                         set { CheckWritable (); description = value; }
309                 }
310                 
311                 [LocalizableAttribute (true)]
312                 public virtual string Title {
313                         get { return title != null ? title : ""; }
314                         set { CheckWritable (); title = value; }
315                 }
316                 
317                 public virtual string Url {
318                         get { return url != null ? url : ""; }
319                         set { CheckWritable (); url = value; }
320                 }
321                 
322                 public IList Roles {
323                         get { return roles; }
324                         set { CheckWritable (); roles = value; }
325                 }
326                 
327                 public bool ReadOnly {
328                         get { return readOnly; }
329                         set { readOnly = value; }
330                 }
331                 
332                 [MonoTODO ("Do somethig with this")]
333                 public string ResourceKey {
334                         get { return resourceKey; }
335                         set { resourceKey = value; }
336                 }
337                 
338                 public string Key { get { return key; } }
339                 public SiteMapProvider Provider { get { return provider; } }
340                 
341                 #endregion
342                 
343                 #region INavigateUIData
344                 IHierarchicalEnumerable System.Web.UI.IHierarchyData.GetChildren () { return ChildNodes; }
345                 IHierarchyData System.Web.UI.IHierarchyData.GetParent ()
346                 {
347                         return ParentNode;
348                 }
349
350                 bool System.Web.UI.IHierarchyData.HasChildren { get { return HasChildNodes; } }
351                 object System.Web.UI.IHierarchyData.Item { get { return this; } }
352                 string System.Web.UI.IHierarchyData.Path { get { return Url; } }
353                 string System.Web.UI.IHierarchyData.Type { get { return "SiteMapNode"; } }
354                 #endregion
355                 
356                 #region INavigateUIData
357                 string INavigateUIData.Name { get { return Title; }  }
358                 string INavigateUIData.NavigateUrl { get { return Url; } }
359                 string INavigateUIData.Value { get { return Title; } }
360                 #endregion
361
362                 #region Fields
363                 SiteMapProvider provider;
364                 string key;
365                 string url;
366                 string title;
367                 string description;
368                 IList roles;
369                 NameValueCollection attributes;
370                 NameValueCollection resourceKeys;
371                 bool readOnly;
372                 string resourceKey;
373                 SiteMapNode parent;
374                 string implicitResourceKey;
375                 SiteMapNodeCollection childNodes;
376                 #endregion
377                 
378         }
379 }
380 #endif
381