TreeView.cs 60 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052
  1. //
  2. // System.Web.UI.WebControls.TreeView.cs
  3. //
  4. // Authors:
  5. // Lluis Sanchez Gual ([email protected])
  6. //
  7. // (C) 2004 Novell, Inc (http://www.novell.com)
  8. //
  9. // Permission is hereby granted, free of charge, to any person obtaining
  10. // a copy of this software and associated documentation files (the
  11. // "Software"), to deal in the Software without restriction, including
  12. // without limitation the rights to use, copy, modify, merge, publish,
  13. // distribute, sublicense, and/or sell copies of the Software, and to
  14. // permit persons to whom the Software is furnished to do so, subject to
  15. // the following conditions:
  16. //
  17. // The above copyright notice and this permission notice shall be
  18. // included in all copies or substantial portions of the Software.
  19. //
  20. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  21. // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
  22. // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  23. // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
  24. // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
  25. // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
  26. // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  27. //
  28. // Copyright (C) 2004 Novell, Inc (http://www.novell.com)
  29. //
  30. #if NET_2_0
  31. using System.Collections;
  32. using System.Text;
  33. using System.ComponentModel;
  34. using System.Globalization;
  35. using System.Web.Handlers;
  36. using System.Collections.Specialized;
  37. using System.IO;
  38. using System.Security.Permissions;
  39. using System.Collections.Generic;
  40. using System.Web.Util;
  41. namespace System.Web.UI.WebControls
  42. {
  43. // CAS
  44. [AspNetHostingPermission (SecurityAction.LinkDemand, Level = AspNetHostingPermissionLevel.Minimal)]
  45. [AspNetHostingPermission (SecurityAction.InheritanceDemand, Level = AspNetHostingPermissionLevel.Minimal)]
  46. // attributes
  47. [SupportsEventValidation]
  48. [ControlValueProperty ("SelectedValue")]
  49. [DefaultEvent ("SelectedNodeChanged")]
  50. [Designer ("System.Web.UI.Design.WebControls.TreeViewDesigner, " + Consts.AssemblySystem_Design, "System.ComponentModel.Design.IDesigner")]
  51. public class TreeView: HierarchicalDataBoundControl, IPostBackEventHandler, IPostBackDataHandler, ICallbackEventHandler
  52. {
  53. string activeSiteMapPath;
  54. bool stylesPrepared;
  55. Style hoverNodeStyle;
  56. TreeNodeStyle leafNodeStyle;
  57. TreeNodeStyle nodeStyle;
  58. TreeNodeStyle parentNodeStyle;
  59. TreeNodeStyle rootNodeStyle;
  60. TreeNodeStyle selectedNodeStyle;
  61. TreeNodeStyleCollection levelStyles;
  62. TreeNodeCollection nodes;
  63. TreeNodeBindingCollection dataBindings;
  64. TreeNode selectedNode;
  65. Hashtable bindings;
  66. int registeredStylesCounter = -1;
  67. List<Style> levelLinkStyles;
  68. Style controlLinkStyle;
  69. Style nodeLinkStyle;
  70. Style rootNodeLinkStyle;
  71. Style parentNodeLinkStyle;
  72. Style leafNodeLinkStyle;
  73. Style selectedNodeLinkStyle;
  74. Style hoverNodeLinkStyle;
  75. static readonly object TreeNodeCheckChangedEvent = new object();
  76. static readonly object SelectedNodeChangedEvent = new object();
  77. static readonly object TreeNodeCollapsedEvent = new object();
  78. static readonly object TreeNodeDataBoundEvent = new object();
  79. static readonly object TreeNodeExpandedEvent = new object();
  80. static readonly object TreeNodePopulateEvent = new object();
  81. static Hashtable imageStyles = new Hashtable ();
  82. class TreeViewExpandDepthConverter : TypeConverter
  83. {
  84. public override bool CanConvertFrom (ITypeDescriptorContext context, Type sourceType)
  85. {
  86. if (sourceType == typeof (string) || sourceType == typeof (int))
  87. return true;
  88. return base.CanConvertFrom (context, sourceType);
  89. }
  90. public override bool CanConvertTo (ITypeDescriptorContext context, Type destinationType)
  91. {
  92. if (destinationType == typeof (string) || destinationType == typeof (int))
  93. return true;
  94. return base.CanConvertTo (context, destinationType);
  95. }
  96. public override object ConvertTo (ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType)
  97. {
  98. if (destinationType != typeof (int) && destinationType != typeof (string))
  99. return base.ConvertTo (context, culture, value, destinationType);
  100. if (value is string) {
  101. if (destinationType == typeof (int)) {
  102. if (String.Compare ("FullyExpand", (string)value, StringComparison.OrdinalIgnoreCase) == 0)
  103. return -1;
  104. try {
  105. return Int32.Parse ((string)value);
  106. } catch (Exception) {
  107. return -1;
  108. }
  109. } else
  110. return value;
  111. }
  112. int val = (int)value;
  113. if (destinationType == typeof (string)) {
  114. if (val == -1)
  115. return "FullyExpand";
  116. return val.ToString ();
  117. }
  118. return value;
  119. }
  120. public override object ConvertFrom (ITypeDescriptorContext context, CultureInfo culture, object value)
  121. {
  122. if (!(value is string) && !(value is int))
  123. return base.ConvertFrom (context, culture, value);
  124. if (value is string) {
  125. if (String.Compare ("FullyExpand", (string)value, StringComparison.OrdinalIgnoreCase) == 0)
  126. return -1;
  127. try {
  128. return Int32.Parse ((string)value);
  129. } catch (Exception) {
  130. return null;
  131. }
  132. }
  133. return value;
  134. }
  135. }
  136. class ImageStyle
  137. {
  138. public ImageStyle (string expand, string collapse, string noExpand, string icon, string iconLeaf, string iconRoot) {
  139. Expand = expand;
  140. Collapse = collapse;
  141. NoExpand = noExpand;
  142. RootIcon = iconRoot;
  143. ParentIcon = icon;
  144. LeafIcon = iconLeaf;
  145. }
  146. public string Expand;
  147. public string Collapse;
  148. public string NoExpand;
  149. public string RootIcon;
  150. public string ParentIcon;
  151. public string LeafIcon;
  152. }
  153. static TreeView ()
  154. {
  155. imageStyles [TreeViewImageSet.Arrows] = new ImageStyle ("arrow_plus", "arrow_minus", "arrow_noexpand", null, null, null);
  156. imageStyles [TreeViewImageSet.BulletedList] = new ImageStyle (null, null, null, "dot_full", "dot_empty", "dot_full");
  157. imageStyles [TreeViewImageSet.BulletedList2] = new ImageStyle (null, null, null, "box_full", "box_empty", "box_full");
  158. imageStyles [TreeViewImageSet.BulletedList3] = new ImageStyle (null, null, null, "star_full", "star_empty", "star_full");
  159. imageStyles [TreeViewImageSet.BulletedList4] = new ImageStyle (null, null, null, "star_full", "star_empty", "dots");
  160. imageStyles [TreeViewImageSet.Contacts] = new ImageStyle ("TreeView_plus", "TreeView_minus", "contact", null, null, null);
  161. imageStyles [TreeViewImageSet.Events] = new ImageStyle (null, null, null, "warning", "warning", "warning");
  162. imageStyles [TreeViewImageSet.Inbox] = new ImageStyle (null, null, null, "inbox", "inbox", "inbox");
  163. imageStyles [TreeViewImageSet.Msdn] = new ImageStyle ("box_plus", "box_minus", "box_noexpand", null, null, null);
  164. imageStyles [TreeViewImageSet.Simple] = new ImageStyle (null, null, "box_full", null, null, null);
  165. imageStyles [TreeViewImageSet.Simple2] = new ImageStyle (null, null, "box_empty", null, null, null);
  166. // TODO
  167. imageStyles [TreeViewImageSet.News] = new ImageStyle ("TreeView_plus", "TreeView_minus", "TreeView_noexpand", null, null, null);
  168. imageStyles [TreeViewImageSet.Faq] = new ImageStyle ("TreeView_plus", "TreeView_minus", "TreeView_noexpand", null, null, null);
  169. imageStyles [TreeViewImageSet.WindowsHelp] = new ImageStyle ("TreeView_plus", "TreeView_minus", "TreeView_noexpand", null, null, null);
  170. imageStyles [TreeViewImageSet.XPFileExplorer] = new ImageStyle ("TreeView_plus", "TreeView_minus", "TreeView_noexpand", "folder", "file", "computer");
  171. }
  172. public event TreeNodeEventHandler TreeNodeCheckChanged {
  173. add { Events.AddHandler (TreeNodeCheckChangedEvent, value); }
  174. remove { Events.RemoveHandler (TreeNodeCheckChangedEvent, value); }
  175. }
  176. public event EventHandler SelectedNodeChanged {
  177. add { Events.AddHandler (SelectedNodeChangedEvent, value); }
  178. remove { Events.RemoveHandler (SelectedNodeChangedEvent, value); }
  179. }
  180. public event TreeNodeEventHandler TreeNodeCollapsed {
  181. add { Events.AddHandler (TreeNodeCollapsedEvent, value); }
  182. remove { Events.RemoveHandler (TreeNodeCollapsedEvent, value); }
  183. }
  184. public event TreeNodeEventHandler TreeNodeDataBound {
  185. add { Events.AddHandler (TreeNodeDataBoundEvent, value); }
  186. remove { Events.RemoveHandler (TreeNodeDataBoundEvent, value); }
  187. }
  188. public event TreeNodeEventHandler TreeNodeExpanded {
  189. add { Events.AddHandler (TreeNodeExpandedEvent, value); }
  190. remove { Events.RemoveHandler (TreeNodeExpandedEvent, value); }
  191. }
  192. public event TreeNodeEventHandler TreeNodePopulate {
  193. add { Events.AddHandler (TreeNodePopulateEvent, value); }
  194. remove { Events.RemoveHandler (TreeNodePopulateEvent, value); }
  195. }
  196. protected virtual void OnTreeNodeCheckChanged (TreeNodeEventArgs e)
  197. {
  198. if (Events != null) {
  199. TreeNodeEventHandler eh = (TreeNodeEventHandler) Events [TreeNodeCheckChangedEvent];
  200. if (eh != null) eh (this, e);
  201. }
  202. }
  203. protected virtual void OnSelectedNodeChanged (EventArgs e)
  204. {
  205. if (Events != null) {
  206. EventHandler eh = (EventHandler) Events [SelectedNodeChangedEvent];
  207. if (eh != null) eh (this, e);
  208. }
  209. }
  210. protected virtual void OnTreeNodeCollapsed (TreeNodeEventArgs e)
  211. {
  212. if (Events != null) {
  213. TreeNodeEventHandler eh = (TreeNodeEventHandler) Events [TreeNodeCollapsedEvent];
  214. if (eh != null) eh (this, e);
  215. }
  216. }
  217. protected virtual void OnTreeNodeDataBound (TreeNodeEventArgs e)
  218. {
  219. if (Events != null) {
  220. TreeNodeEventHandler eh = (TreeNodeEventHandler) Events [TreeNodeDataBoundEvent];
  221. if (eh != null) eh (this, e);
  222. }
  223. }
  224. protected virtual void OnTreeNodeExpanded (TreeNodeEventArgs e)
  225. {
  226. if (Events != null) {
  227. TreeNodeEventHandler eh = (TreeNodeEventHandler) Events [TreeNodeExpandedEvent];
  228. if (eh != null) eh (this, e);
  229. }
  230. }
  231. protected virtual void OnTreeNodePopulate (TreeNodeEventArgs e)
  232. {
  233. if (Events != null) {
  234. TreeNodeEventHandler eh = (TreeNodeEventHandler) Events [TreeNodePopulateEvent];
  235. if (eh != null) eh (this, e);
  236. }
  237. }
  238. [Localizable (true)]
  239. public string CollapseImageToolTip {
  240. get {
  241. return ViewState.GetString ("CollapseImageToolTip", "Collapse {0}");
  242. }
  243. set {
  244. ViewState["CollapseImageToolTip"] = value;
  245. }
  246. }
  247. [MonoTODO ("Implement support for this")]
  248. [WebCategory ("Behavior")]
  249. [WebSysDescription ("Whether the tree will automatically generate bindings.")]
  250. [DefaultValue (true)]
  251. public bool AutoGenerateDataBindings {
  252. get {
  253. return ViewState.GetBool ("AutoGenerateDataBindings", true);
  254. }
  255. set {
  256. ViewState["AutoGenerateDataBindings"] = value;
  257. }
  258. }
  259. [DefaultValue ("")]
  260. [WebSysDescription ("The url of the image to show when a node can be collapsed.")]
  261. [UrlProperty]
  262. [WebCategory ("Appearance")]
  263. [Editor ("System.Web.UI.Design.ImageUrlEditor, " + Consts.AssemblySystem_Design, "System.Drawing.Design.UITypeEditor, " + Consts.AssemblySystem_Drawing)]
  264. public string CollapseImageUrl {
  265. get {
  266. return ViewState.GetString ("CollapseImageUrl", "");
  267. }
  268. set {
  269. ViewState["CollapseImageUrl"] = value;
  270. }
  271. }
  272. [WebCategory ("Data")]
  273. [PersistenceMode (PersistenceMode.InnerProperty)]
  274. [WebSysDescription ("Bindings for tree nodes.")]
  275. [Editor ("System.Web.UI.Design.WebControls.TreeViewBindingsEditor, " + Consts.AssemblySystem_Design, "System.Drawing.Design.UITypeEditor, " + Consts.AssemblySystem_Drawing)]
  276. [DefaultValue (null)]
  277. [MergablePropertyAttribute (false)]
  278. public TreeNodeBindingCollection DataBindings {
  279. get {
  280. if (dataBindings == null) {
  281. dataBindings = new TreeNodeBindingCollection ();
  282. if (IsTrackingViewState)
  283. ((IStateManager)dataBindings).TrackViewState();
  284. }
  285. return dataBindings;
  286. }
  287. }
  288. [WebCategory ("Behavior")]
  289. [WebSysDescription ("Whether the tree view can use client-side script to expand and collapse nodes.")]
  290. [Themeable (false)]
  291. [DefaultValue (true)]
  292. public bool EnableClientScript {
  293. get {
  294. return ViewState.GetBool ("EnableClientScript", true);
  295. }
  296. set {
  297. ViewState["EnableClientScript"] = value;
  298. }
  299. }
  300. [DefaultValue (-1)]
  301. [WebCategory ("Behavior")]
  302. [WebSysDescription ("The initial expand depth.")]
  303. [TypeConverter ("System.Web.UI.WebControls.TreeView+TreeViewExpandDepthConverter, " + Consts.AssemblySystem_Web)]
  304. public int ExpandDepth {
  305. get {
  306. return ViewState.GetInt ("ExpandDepth", -1);
  307. }
  308. set {
  309. ViewState["ExpandDepth"] = value;
  310. }
  311. }
  312. [Localizable (true)]
  313. public string ExpandImageToolTip {
  314. get {
  315. return ViewState.GetString ("ExpandImageToolTip", "Expand {0}");
  316. }
  317. set {
  318. ViewState["ExpandImageToolTip"] = value;
  319. }
  320. }
  321. [DefaultValue ("")]
  322. [UrlProperty]
  323. [WebSysDescription ("The url of the image to show when a node can be expanded.")]
  324. [WebCategory ("Appearance")]
  325. [Editor ("System.Web.UI.Design.ImageUrlEditor, " + Consts.AssemblySystem_Design, "System.Drawing.Design.UITypeEditor, " + Consts.AssemblySystem_Drawing)]
  326. public string ExpandImageUrl {
  327. get {
  328. return ViewState.GetString ("ExpandImageUrl", "");
  329. }
  330. set {
  331. ViewState["ExpandImageUrl"] = value;
  332. }
  333. }
  334. [PersistenceMode (PersistenceMode.InnerProperty)]
  335. [NotifyParentProperty (true)]
  336. [DefaultValue (null)]
  337. [WebCategory ("Styles")]
  338. [DesignerSerializationVisibility (DesignerSerializationVisibility.Content)]
  339. public Style HoverNodeStyle {
  340. get {
  341. if (hoverNodeStyle == null) {
  342. hoverNodeStyle = new Style();
  343. if (IsTrackingViewState)
  344. hoverNodeStyle.TrackViewState();
  345. }
  346. return hoverNodeStyle;
  347. }
  348. }
  349. [DefaultValue (TreeViewImageSet.Custom)]
  350. public TreeViewImageSet ImageSet {
  351. get {
  352. return (TreeViewImageSet)ViewState.GetInt ("ImageSet", (int)TreeViewImageSet.Custom);
  353. }
  354. set {
  355. if (!Enum.IsDefined (typeof (TreeViewImageSet), value))
  356. throw new ArgumentOutOfRangeException ();
  357. ViewState["ImageSet"] = value;
  358. }
  359. }
  360. [PersistenceMode (PersistenceMode.InnerProperty)]
  361. [NotifyParentProperty (true)]
  362. [DefaultValue (null)]
  363. [WebCategory ("Styles")]
  364. [DesignerSerializationVisibility (DesignerSerializationVisibility.Content)]
  365. public TreeNodeStyle LeafNodeStyle {
  366. get {
  367. if (leafNodeStyle == null) {
  368. leafNodeStyle = new TreeNodeStyle ();
  369. if (IsTrackingViewState)
  370. leafNodeStyle.TrackViewState();
  371. }
  372. return leafNodeStyle;
  373. }
  374. }
  375. [DefaultValue (null)]
  376. [WebCategory ("Styles")]
  377. [PersistenceMode (PersistenceMode.InnerProperty)]
  378. [Editor ("System.Web.UI.Design.WebControls.TreeNodeStyleCollectionEditor," + Consts.AssemblySystem_Design, "System.Drawing.Design.UITypeEditor, " + Consts.AssemblySystem_Drawing)]
  379. public TreeNodeStyleCollection LevelStyles {
  380. get {
  381. if (levelStyles == null) {
  382. levelStyles = new TreeNodeStyleCollection ();
  383. if (IsTrackingViewState)
  384. ((IStateManager)levelStyles).TrackViewState();
  385. }
  386. return levelStyles;
  387. }
  388. }
  389. [DefaultValue ("")]
  390. public string LineImagesFolder {
  391. get {
  392. return ViewState.GetString ("LineImagesFolder", "");
  393. }
  394. set {
  395. ViewState["LineImagesFolder"] = value;
  396. }
  397. }
  398. [DefaultValue (-1)]
  399. public int MaxDataBindDepth {
  400. get {
  401. return ViewState.GetInt ("MaxDataBindDepth", -1);
  402. }
  403. set {
  404. ViewState["MaxDataBindDepth"] = value;
  405. }
  406. }
  407. [DefaultValue (20)]
  408. public int NodeIndent {
  409. get {
  410. return ViewState.GetInt ("NodeIndent", 20);
  411. }
  412. set {
  413. ViewState["NodeIndent"] = value;
  414. }
  415. }
  416. [PersistenceMode (PersistenceMode.InnerProperty)]
  417. [Editor ("System.Web.UI.Design.WebControls.TreeNodeCollectionEditor," + Consts.AssemblySystem_Design, "System.Drawing.Design.UITypeEditor, " + Consts.AssemblySystem_Drawing)]
  418. [DefaultValueAttribute (null)]
  419. [MergablePropertyAttribute (false)]
  420. public TreeNodeCollection Nodes {
  421. get {
  422. if (nodes == null) {
  423. nodes = new TreeNodeCollection (this);
  424. if (IsTrackingViewState)
  425. ((IStateManager)nodes).TrackViewState();
  426. }
  427. return nodes;
  428. }
  429. }
  430. [PersistenceMode (PersistenceMode.InnerProperty)]
  431. [NotifyParentProperty (true)]
  432. [DefaultValue (null)]
  433. [WebCategory ("Styles")]
  434. [DesignerSerializationVisibility (DesignerSerializationVisibility.Content)]
  435. public TreeNodeStyle NodeStyle {
  436. get {
  437. if (nodeStyle == null) {
  438. nodeStyle = new TreeNodeStyle ();
  439. if (IsTrackingViewState)
  440. nodeStyle.TrackViewState();
  441. }
  442. return nodeStyle;
  443. }
  444. }
  445. [DefaultValue (false)]
  446. public bool NodeWrap {
  447. get {
  448. return ViewState.GetBool ("NodeWrap", false);
  449. }
  450. set {
  451. ViewState ["NodeWrap"] = value;
  452. }
  453. }
  454. [UrlProperty]
  455. [DefaultValue ("")]
  456. [WebSysDescription ("The url of the image to show for leaf nodes.")]
  457. [WebCategory ("Appearance")]
  458. [Editor ("System.Web.UI.Design.ImageUrlEditor, " + Consts.AssemblySystem_Design, "System.Drawing.Design.UITypeEditor, " + Consts.AssemblySystem_Drawing)]
  459. public string NoExpandImageUrl {
  460. get {
  461. return ViewState.GetString ("NoExpandImageUrl", "");
  462. }
  463. set {
  464. ViewState ["NoExpandImageUrl"] = value;
  465. }
  466. }
  467. [PersistenceMode (PersistenceMode.InnerProperty)]
  468. [NotifyParentProperty (true)]
  469. [DefaultValue (null)]
  470. [WebCategory ("Styles")]
  471. [DesignerSerializationVisibility (DesignerSerializationVisibility.Content)]
  472. public TreeNodeStyle ParentNodeStyle {
  473. get {
  474. if (parentNodeStyle == null) {
  475. parentNodeStyle = new TreeNodeStyle ();
  476. if (IsTrackingViewState)
  477. parentNodeStyle.TrackViewState();
  478. }
  479. return parentNodeStyle;
  480. }
  481. }
  482. [DefaultValue ('/')]
  483. public char PathSeparator {
  484. get {
  485. return ViewState.GetChar ("PathSeparator", '/');
  486. }
  487. set {
  488. ViewState ["PathSeparator"] = value;
  489. }
  490. }
  491. [DefaultValue (true)]
  492. public bool PopulateNodesFromClient {
  493. get {
  494. return ViewState.GetBool ("PopulateNodesFromClient", true);
  495. }
  496. set {
  497. ViewState ["PopulateNodesFromClient"] = value;
  498. }
  499. }
  500. [PersistenceMode (PersistenceMode.InnerProperty)]
  501. [NotifyParentProperty (true)]
  502. [DefaultValue (null)]
  503. [WebCategory ("Styles")]
  504. [DesignerSerializationVisibility (DesignerSerializationVisibility.Content)]
  505. public TreeNodeStyle RootNodeStyle {
  506. get {
  507. if (rootNodeStyle == null) {
  508. rootNodeStyle = new TreeNodeStyle ();
  509. if (IsTrackingViewState)
  510. rootNodeStyle.TrackViewState();
  511. }
  512. return rootNodeStyle;
  513. }
  514. }
  515. [PersistenceMode (PersistenceMode.InnerProperty)]
  516. [NotifyParentProperty (true)]
  517. [DefaultValue (null)]
  518. [WebCategory ("Styles")]
  519. [DesignerSerializationVisibility (DesignerSerializationVisibility.Content)]
  520. public TreeNodeStyle SelectedNodeStyle {
  521. get {
  522. if (selectedNodeStyle == null) {
  523. selectedNodeStyle = new TreeNodeStyle ();
  524. if (IsTrackingViewState)
  525. selectedNodeStyle.TrackViewState();
  526. }
  527. return selectedNodeStyle;
  528. }
  529. }
  530. Style ControlLinkStyle {
  531. get {
  532. if (controlLinkStyle == null) {
  533. controlLinkStyle = new Style ();
  534. controlLinkStyle.AlwaysRenderTextDecoration = true;
  535. }
  536. return controlLinkStyle;
  537. }
  538. }
  539. Style NodeLinkStyle {
  540. get {
  541. if (nodeLinkStyle == null) {
  542. nodeLinkStyle = new Style ();
  543. }
  544. return nodeLinkStyle;
  545. }
  546. }
  547. Style RootNodeLinkStyle {
  548. get {
  549. if (rootNodeLinkStyle == null) {
  550. rootNodeLinkStyle = new Style ();
  551. }
  552. return rootNodeLinkStyle;
  553. }
  554. }
  555. Style ParentNodeLinkStyle {
  556. get {
  557. if (parentNodeLinkStyle == null) {
  558. parentNodeLinkStyle = new Style ();
  559. }
  560. return parentNodeLinkStyle;
  561. }
  562. }
  563. Style SelectedNodeLinkStyle {
  564. get {
  565. if (selectedNodeLinkStyle == null) {
  566. selectedNodeLinkStyle = new Style ();
  567. }
  568. return selectedNodeLinkStyle;
  569. }
  570. }
  571. Style LeafNodeLinkStyle {
  572. get {
  573. if (leafNodeLinkStyle == null) {
  574. leafNodeLinkStyle = new Style ();
  575. }
  576. return leafNodeLinkStyle;
  577. }
  578. }
  579. Style HoverNodeLinkStyle {
  580. get {
  581. if (hoverNodeLinkStyle == null) {
  582. hoverNodeLinkStyle = new Style ();
  583. }
  584. return hoverNodeLinkStyle;
  585. }
  586. }
  587. [DefaultValue (TreeNodeTypes.None)]
  588. public TreeNodeTypes ShowCheckBoxes {
  589. get {
  590. return (TreeNodeTypes)ViewState.GetInt ("ShowCheckBoxes", (int)TreeNodeTypes.None);
  591. }
  592. set {
  593. if ((int) value > 7)
  594. throw new ArgumentOutOfRangeException ();
  595. ViewState ["ShowCheckBoxes"] = value;
  596. }
  597. }
  598. [DefaultValue (true)]
  599. public bool ShowExpandCollapse {
  600. get {
  601. return ViewState.GetBool ("ShowExpandCollapse", true);
  602. }
  603. set {
  604. ViewState ["ShowExpandCollapse"] = value;
  605. }
  606. }
  607. [DefaultValue (false)]
  608. public bool ShowLines {
  609. get {
  610. return ViewState.GetBool ("ShowLines", false);
  611. }
  612. set {
  613. ViewState ["ShowLines"] = value;
  614. }
  615. }
  616. [Localizable (true)]
  617. public string SkipLinkText
  618. {
  619. get {
  620. return ViewState.GetString ("SkipLinkText", "Skip Navigation Links.");
  621. }
  622. set {
  623. ViewState ["SkipLinkText"] = value;
  624. }
  625. }
  626. [Browsable (false)]
  627. [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
  628. public TreeNode SelectedNode {
  629. get { return selectedNode; }
  630. }
  631. [Browsable (false)]
  632. [DefaultValue ("")]
  633. [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
  634. public string SelectedValue {
  635. get { return selectedNode != null ? selectedNode.Value : ""; }
  636. }
  637. [DefaultValue ("")]
  638. public string Target {
  639. get {
  640. return ViewState.GetString ("Target", "");
  641. }
  642. set {
  643. ViewState ["Target"] = value;
  644. }
  645. }
  646. [MonoTODO ("why override?")]
  647. public override bool Visible
  648. {
  649. get {
  650. return base.Visible;
  651. }
  652. set {
  653. base.Visible = value;
  654. }
  655. }
  656. [Browsable (false)]
  657. [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
  658. public TreeNodeCollection CheckedNodes {
  659. get {
  660. TreeNodeCollection col = new TreeNodeCollection ();
  661. FindCheckedNodes (Nodes, col);
  662. return col;
  663. }
  664. }
  665. void FindCheckedNodes (TreeNodeCollection nodeList, TreeNodeCollection result)
  666. {
  667. foreach (TreeNode node in nodeList) {
  668. if (node.Checked) result.Add (node, false);
  669. FindCheckedNodes (node.ChildNodes, result);
  670. }
  671. }
  672. public void ExpandAll ()
  673. {
  674. foreach (TreeNode node in Nodes)
  675. node.ExpandAll ();
  676. }
  677. public void CollapseAll ()
  678. {
  679. foreach (TreeNode node in Nodes)
  680. node.CollapseAll ();
  681. }
  682. public TreeNode FindNode (string valuePath)
  683. {
  684. if (valuePath == null) throw new ArgumentNullException ("valuePath");
  685. string[] path = valuePath.Split (PathSeparator);
  686. int n = 0;
  687. TreeNodeCollection col = Nodes;
  688. bool foundBranch = true;
  689. while (col.Count > 0 && foundBranch) {
  690. foundBranch = false;
  691. foreach (TreeNode node in col) {
  692. if (node.Value == path [n]) {
  693. if (++n == path.Length) return node;
  694. col = node.ChildNodes;
  695. foundBranch = true;
  696. break;
  697. }
  698. }
  699. }
  700. return null;
  701. }
  702. ImageStyle GetImageStyle ()
  703. {
  704. if (ImageSet != TreeViewImageSet.Custom)
  705. return (ImageStyle) imageStyles [ImageSet];
  706. else
  707. return null;
  708. }
  709. protected override HtmlTextWriterTag TagKey {
  710. get { return HtmlTextWriterTag.Div; }
  711. }
  712. protected internal virtual TreeNode CreateNode ()
  713. {
  714. return new TreeNode (this);
  715. }
  716. public sealed override void DataBind ()
  717. {
  718. base.DataBind ();
  719. }
  720. protected void SetNodeDataBound (TreeNode node, bool dataBound)
  721. {
  722. node.SetDataBound (dataBound);
  723. }
  724. protected void SetNodeDataPath (TreeNode node, string dataPath)
  725. {
  726. node.SetDataPath (dataPath);
  727. }
  728. protected void SetNodeDataItem (TreeNode node, object dataItem)
  729. {
  730. node.SetDataItem (dataItem);
  731. }
  732. protected internal override void OnInit (EventArgs e)
  733. {
  734. base.OnInit (e);
  735. }
  736. internal void SetSelectedNode (TreeNode node, bool loading)
  737. {
  738. if (selectedNode == node) return;
  739. if (selectedNode != null)
  740. selectedNode.SelectedFlag = false;
  741. selectedNode = node;
  742. if (!loading)
  743. OnSelectedNodeChanged (new TreeNodeEventArgs (selectedNode));
  744. }
  745. internal void NotifyCheckChanged (TreeNode node)
  746. {
  747. OnTreeNodeCheckChanged (new TreeNodeEventArgs (node));
  748. }
  749. internal void NotifyExpandedChanged (TreeNode node)
  750. {
  751. if (node.Expanded.HasValue && node.Expanded.Value)
  752. OnTreeNodeExpanded (new TreeNodeEventArgs (node));
  753. else if (node.Expanded.HasValue && node.IsParentNode)
  754. OnTreeNodeCollapsed (new TreeNodeEventArgs (node));
  755. }
  756. internal void NotifyPopulateRequired (TreeNode node)
  757. {
  758. OnTreeNodePopulate (new TreeNodeEventArgs (node));
  759. }
  760. protected override void TrackViewState()
  761. {
  762. EnsureDataBound ();
  763. base.TrackViewState();
  764. if (hoverNodeStyle != null) {
  765. hoverNodeStyle.TrackViewState();
  766. }
  767. if (leafNodeStyle != null) {
  768. leafNodeStyle.TrackViewState();
  769. }
  770. if (levelStyles != null && levelStyles.Count > 0) {
  771. ((IStateManager)levelStyles).TrackViewState();
  772. }
  773. if (nodeStyle != null) {
  774. nodeStyle.TrackViewState();
  775. }
  776. if (parentNodeStyle != null) {
  777. parentNodeStyle.TrackViewState();
  778. }
  779. if (rootNodeStyle != null) {
  780. rootNodeStyle.TrackViewState();
  781. }
  782. if (selectedNodeStyle != null) {
  783. selectedNodeStyle.TrackViewState();
  784. }
  785. if (dataBindings != null) {
  786. ((IStateManager)dataBindings).TrackViewState ();
  787. }
  788. if (nodes != null) {
  789. ((IStateManager)nodes).TrackViewState();;
  790. }
  791. }
  792. protected override object SaveViewState()
  793. {
  794. object[] states = new object [10];
  795. states[0] = base.SaveViewState();
  796. states[1] = (hoverNodeStyle == null ? null : hoverNodeStyle.SaveViewState());
  797. states[2] = (leafNodeStyle == null ? null : leafNodeStyle.SaveViewState());
  798. states[3] = (levelStyles == null ? null : ((IStateManager)levelStyles).SaveViewState());
  799. states[4] = (nodeStyle == null ? null : nodeStyle.SaveViewState());
  800. states[5] = (parentNodeStyle == null ? null : parentNodeStyle.SaveViewState());
  801. states[6] = (rootNodeStyle == null ? null : rootNodeStyle.SaveViewState());
  802. states[7] = (selectedNodeStyle == null ? null : selectedNodeStyle.SaveViewState());
  803. states[8] = (dataBindings == null ? null : ((IStateManager)dataBindings).SaveViewState());
  804. states[9] = (nodes == null ? null : ((IStateManager)nodes).SaveViewState());
  805. for (int i = states.Length - 1; i >= 0; i--) {
  806. if (states [i] != null)
  807. return states;
  808. }
  809. return null;
  810. }
  811. protected override void LoadViewState (object savedState)
  812. {
  813. if (savedState == null)
  814. return;
  815. object [] states = (object []) savedState;
  816. base.LoadViewState (states[0]);
  817. if (states[1] != null)
  818. HoverNodeStyle.LoadViewState (states[1]);
  819. if (states[2] != null)
  820. LeafNodeStyle.LoadViewState(states[2]);
  821. if (states[3] != null)
  822. ((IStateManager)LevelStyles).LoadViewState(states[3]);
  823. if (states[4] != null)
  824. NodeStyle.LoadViewState(states[4]);
  825. if (states[5] != null)
  826. ParentNodeStyle.LoadViewState(states[5]);
  827. if (states[6] != null)
  828. RootNodeStyle.LoadViewState(states[6]);
  829. if (states[7] != null)
  830. SelectedNodeStyle.LoadViewState(states[7]);
  831. if (states[8] != null)
  832. ((IStateManager)DataBindings).LoadViewState(states[8]);
  833. if (states[9] != null)
  834. ((IStateManager)Nodes).LoadViewState(states[9]);
  835. }
  836. protected virtual void RaisePostBackEvent (string eventArgument)
  837. {
  838. ValidateEvent (UniqueID, eventArgument);
  839. string[] args = eventArgument.Split ('|');
  840. TreeNode node = FindNodeByPos (args[1]);
  841. if (node == null) return;
  842. if (args [0] == "sel")
  843. HandleSelectEvent (node);
  844. else if (args [0] == "ec")
  845. HandleExpandCollapseEvent (node);
  846. }
  847. void HandleSelectEvent (TreeNode node)
  848. {
  849. switch (node.SelectAction) {
  850. case TreeNodeSelectAction.Select:
  851. node.Select ();
  852. break;
  853. case TreeNodeSelectAction.Expand:
  854. node.Expand ();
  855. break;
  856. case TreeNodeSelectAction.SelectExpand:
  857. node.Select ();
  858. node.Expand ();
  859. break;
  860. }
  861. }
  862. void HandleExpandCollapseEvent (TreeNode node)
  863. {
  864. node.ToggleExpandState ();
  865. }
  866. protected virtual void RaisePostDataChangedEvent ()
  867. {
  868. }
  869. TreeNode MakeNodeTree (string[] args)
  870. {
  871. string[] segments = args [0].Split ('_');
  872. TreeNode ret = null, node;
  873. StringBuilder sb = new StringBuilder ();
  874. foreach (string seg in segments) {
  875. int idx = Int32.Parse (seg);
  876. node = new TreeNode (seg);
  877. if (ret != null) {
  878. ret.ChildNodes.Add (node);
  879. node.Index = idx;
  880. }
  881. ret = node;
  882. }
  883. ret.Value = args [1].Replace ("U+007C", "|");
  884. ret.ImageUrl = args [2].Replace ("U+007C", "|");
  885. ret.NavigateUrl = args [3].Replace ("U+007C", "|");
  886. ret.Target = args [4].Replace ("U+007C", "|");
  887. ret.Tree = this;
  888. NotifyPopulateRequired (ret);
  889. return ret;
  890. }
  891. string callbackResult;
  892. protected virtual void RaiseCallbackEvent (string eventArgs)
  893. {
  894. string[] args = eventArgs.Split ('|');
  895. RequiresDataBinding = true;
  896. EnsureDataBound ();
  897. TreeNode node = MakeNodeTree (args);
  898. ArrayList levelLines = new ArrayList ();
  899. TreeNode nd = node;
  900. while (nd != null) {
  901. int childCount = nd.Parent != null ? nd.Parent.ChildNodes.Count : Nodes.Count;
  902. levelLines.Insert (0, (nd.Index < childCount - 1) ? this : null);
  903. nd = nd.Parent;
  904. }
  905. StringWriter sw = new StringWriter ();
  906. HtmlTextWriter writer = new HtmlTextWriter (sw);
  907. EnsureStylesPrepared ();
  908. node.Expanded = true;
  909. int num = node.ChildNodes.Count;
  910. for (int n=0; n<num; n++)
  911. RenderNode (writer, node.ChildNodes [n], node.Depth + 1, levelLines, true, n<num-1);
  912. string res = sw.ToString ();
  913. callbackResult = res.Length > 0 ? res : "*";
  914. }
  915. protected virtual string GetCallbackResult ()
  916. {
  917. return callbackResult;
  918. }
  919. void IPostBackEventHandler.RaisePostBackEvent (string eventArgument)
  920. {
  921. RaisePostBackEvent (eventArgument);
  922. }
  923. bool IPostBackDataHandler.LoadPostData (string postDataKey, NameValueCollection postCollection)
  924. {
  925. return LoadPostData (postDataKey, postCollection);
  926. }
  927. void IPostBackDataHandler.RaisePostDataChangedEvent ()
  928. {
  929. RaisePostDataChangedEvent ();
  930. }
  931. void ICallbackEventHandler.RaiseCallbackEvent (string eventArgs)
  932. {
  933. RaiseCallbackEvent (eventArgs);
  934. }
  935. string ICallbackEventHandler.GetCallbackResult ()
  936. {
  937. return GetCallbackResult ();
  938. }
  939. protected override ControlCollection CreateControlCollection ()
  940. {
  941. return new EmptyControlCollection (this);
  942. }
  943. protected internal override void PerformDataBinding ()
  944. {
  945. base.PerformDataBinding ();
  946. InitializeDataBindings ();
  947. HierarchicalDataSourceView data = GetData ("");
  948. if (data == null)
  949. return;
  950. Nodes.Clear ();
  951. IHierarchicalEnumerable e = data.Select ();
  952. FillBoundChildrenRecursive (e, Nodes);
  953. }
  954. void FillBoundChildrenRecursive (IHierarchicalEnumerable hEnumerable, TreeNodeCollection nodeCollection)
  955. {
  956. if (hEnumerable == null)
  957. return;
  958. foreach (object obj in hEnumerable) {
  959. IHierarchyData hdata = hEnumerable.GetHierarchyData (obj);
  960. TreeNode child = new TreeNode ();
  961. nodeCollection.Add (child);
  962. child.Bind (hdata);
  963. OnTreeNodeDataBound (new TreeNodeEventArgs (child));
  964. if (MaxDataBindDepth >= 0 && child.Depth == MaxDataBindDepth)
  965. continue;
  966. if (hdata == null || !hdata.HasChildren)
  967. continue;
  968. IHierarchicalEnumerable e = hdata.GetChildren ();
  969. FillBoundChildrenRecursive (e, child.ChildNodes);
  970. }
  971. }
  972. protected virtual bool LoadPostData (string postDataKey, NameValueCollection postCollection)
  973. {
  974. bool res = false;
  975. if (EnableClientScript && PopulateNodesFromClient) {
  976. string states = postCollection [ClientID + "_PopulatedStates"];
  977. if (states != null) {
  978. foreach (string id in states.Split ('|')) {
  979. if (String.IsNullOrEmpty(id))
  980. continue;
  981. TreeNode node = FindNodeByPos (id);
  982. if (node != null && node.PopulateOnDemand && !node.Populated)
  983. node.Populated = true;
  984. }
  985. }
  986. res = true;
  987. }
  988. UnsetCheckStates (Nodes, postCollection);
  989. SetCheckStates (postCollection);
  990. if (EnableClientScript) {
  991. string states = postCollection [ClientID + "_ExpandStates"];
  992. if (states != null) {
  993. string[] ids = states.Split ('|');
  994. UnsetExpandStates (Nodes, ids);
  995. SetExpandStates (ids);
  996. }
  997. else
  998. UnsetExpandStates (Nodes, new string[0]);
  999. res = true;
  1000. }
  1001. return res;
  1002. }
  1003. const string _OnPreRender_Script_Preamble =
  1004. "var {0} = new Object ();\n" +
  1005. "{0}.treeId = {1};\n" +
  1006. "{0}.uid = {2};\n" +
  1007. "{0}.showImage = {3};\n";
  1008. const string _OnPreRender_Script_ShowExpandCollapse =
  1009. "{0}.expandImage = {1};\n" +
  1010. "{0}.collapseImage = {2};\n";
  1011. const string _OnPreRender_Script_ShowExpandCollapse_Populate =
  1012. "{0}.noExpandImage = {1};\n";
  1013. const string _OnPreRender_Script_PopulateCallback =
  1014. "{0}.form = {1};\n" +
  1015. "{0}.PopulateNode = function (nodeId, nodeValue, nodeImageUrl, nodeNavigateUrl, nodeTarget) {{\n" +
  1016. "\t{2}.__theFormPostData = \"\";\n" +
  1017. "\t{2}.__theFormPostCollection = new Array ();\n" +
  1018. "\t{2}.WebForm_InitCallback ();\n" +
  1019. "\tTreeView_PopulateNode (this.uid, this.treeId, nodeId, nodeValue, nodeImageUrl, nodeNavigateUrl, nodeTarget)\n}};\n";
  1020. const string _OnPreRender_Script_CallbackOptions =
  1021. "{0}.populateFromClient = {1};\n" +
  1022. "{0}.expandAlt = {2};\n" +
  1023. "{0}.collapseAlt = {3};\n";
  1024. const string _OnPreRender_Script_HoverStyle =
  1025. "{0}.hoverClass = {1};\n" +
  1026. "{0}.hoverLinkClass = {2};\n";
  1027. protected internal override void OnPreRender (EventArgs e)
  1028. {
  1029. base.OnPreRender (e);
  1030. if (Page != null) {
  1031. if (Enabled)
  1032. Page.RegisterRequiresPostBack (this);
  1033. if (EnableClientScript && !Page.ClientScript.IsClientScriptIncludeRegistered (typeof(TreeView), "TreeView.js")) {
  1034. string url = Page.ClientScript.GetWebResourceUrl (typeof(TreeView), "TreeView.js");
  1035. Page.ClientScript.RegisterClientScriptInclude (typeof(TreeView), "TreeView.js", url);
  1036. }
  1037. }
  1038. string ctree = ClientID + "_data";
  1039. StringBuilder script = new StringBuilder ();
  1040. script.AppendFormat (_OnPreRender_Script_Preamble,
  1041. ctree,
  1042. ClientScriptManager.GetScriptLiteral (ClientID),
  1043. ClientScriptManager.GetScriptLiteral (UniqueID),
  1044. ClientScriptManager.GetScriptLiteral (ShowExpandCollapse));
  1045. if (ShowExpandCollapse) {
  1046. ImageStyle imageStyle = GetImageStyle ();
  1047. script.AppendFormat (_OnPreRender_Script_ShowExpandCollapse,
  1048. ctree,
  1049. ClientScriptManager.GetScriptLiteral (GetNodeImageUrl ("plus", imageStyle)),
  1050. ClientScriptManager.GetScriptLiteral (GetNodeImageUrl ("minus", imageStyle)));
  1051. if (PopulateNodesFromClient)
  1052. script.AppendFormat (_OnPreRender_Script_ShowExpandCollapse_Populate,
  1053. ctree,
  1054. ClientScriptManager.GetScriptLiteral (GetNodeImageUrl ("noexpand", imageStyle)));
  1055. }
  1056. if (Page != null) {
  1057. script.AppendFormat (_OnPreRender_Script_PopulateCallback,
  1058. ctree,
  1059. Page.theForm,
  1060. Page.WebFormScriptReference);
  1061. // Page.ClientScript.GetCallbackEventReference (
  1062. // "this.uid", "nodeId",
  1063. // "TreeView_PopulateCallback",
  1064. // "this.treeId + \" \" + nodeId", "TreeView_PopulateCallback", false));
  1065. script.AppendFormat (_OnPreRender_Script_CallbackOptions,
  1066. ctree,
  1067. ClientScriptManager.GetScriptLiteral (PopulateNodesFromClient),
  1068. ClientScriptManager.GetScriptLiteral (GetNodeImageToolTip (true, null)),
  1069. ClientScriptManager.GetScriptLiteral (GetNodeImageToolTip (false, null)));
  1070. if (!Page.IsPostBack) {
  1071. SetNodesExpandedToDepthRecursive (Nodes);
  1072. }
  1073. if (EnableClientScript) {
  1074. Page.ClientScript.RegisterHiddenField (ClientID + "_ExpandStates", GetExpandStates ());
  1075. // Make sure the basic script infrastructure is rendered
  1076. Page.ClientScript.RegisterWebFormClientScript ();
  1077. }
  1078. if (EnableClientScript && PopulateNodesFromClient) {
  1079. Page.ClientScript.RegisterHiddenField (ClientID + "_PopulatedStates", "|");
  1080. }
  1081. EnsureStylesPrepared ();
  1082. if (hoverNodeStyle != null) {
  1083. if (Page.Header == null)
  1084. throw new InvalidOperationException ("Using TreeView.HoverNodeStyle requires Page.Header to be non-null (e.g. <head runat=\"server\" />).");
  1085. RegisterStyle (HoverNodeStyle, HoverNodeLinkStyle);
  1086. script.AppendFormat (_OnPreRender_Script_HoverStyle,
  1087. ctree,
  1088. ClientScriptManager.GetScriptLiteral (HoverNodeStyle.RegisteredCssClass),
  1089. ClientScriptManager.GetScriptLiteral (HoverNodeLinkStyle.RegisteredCssClass));
  1090. }
  1091. Page.ClientScript.RegisterStartupScript (typeof(TreeView), this.UniqueID, script.ToString (), true);
  1092. script = null;
  1093. }
  1094. }
  1095. void EnsureStylesPrepared () {
  1096. if (stylesPrepared)
  1097. return;
  1098. stylesPrepared = true;
  1099. PrepareStyles ();
  1100. }
  1101. void PrepareStyles () {
  1102. // The order in which styles are defined matters when more than one class
  1103. // is assigned to an element
  1104. ControlLinkStyle.CopyTextStylesFrom (ControlStyle);
  1105. RegisterStyle (ControlLinkStyle);
  1106. if (nodeStyle != null)
  1107. RegisterStyle (NodeStyle, NodeLinkStyle);
  1108. if (rootNodeStyle != null)
  1109. RegisterStyle (RootNodeStyle, RootNodeLinkStyle);
  1110. if (parentNodeStyle != null)
  1111. RegisterStyle (ParentNodeStyle, ParentNodeLinkStyle);
  1112. if (leafNodeStyle != null)
  1113. RegisterStyle (LeafNodeStyle, LeafNodeLinkStyle);
  1114. if (levelStyles != null && levelStyles.Count > 0) {
  1115. levelLinkStyles = new List<Style> (levelStyles.Count);
  1116. foreach (Style style in levelStyles) {
  1117. Style linkStyle = new Style ();
  1118. levelLinkStyles.Add (linkStyle);
  1119. RegisterStyle (style, linkStyle);
  1120. }
  1121. }
  1122. if (selectedNodeStyle != null)
  1123. RegisterStyle (SelectedNodeStyle, SelectedNodeLinkStyle);
  1124. }
  1125. void SetNodesExpandedToDepthRecursive (TreeNodeCollection nodes) {
  1126. foreach (TreeNode node in nodes) {
  1127. if (!node.Expanded.HasValue) {
  1128. if (ExpandDepth < 0 || node.Depth < ExpandDepth)
  1129. node.Expanded = true;
  1130. }
  1131. SetNodesExpandedToDepthRecursive (node.ChildNodes);
  1132. }
  1133. }
  1134. string IncrementStyleClassName () {
  1135. registeredStylesCounter++;
  1136. return ClientID + "_" + registeredStylesCounter;
  1137. }
  1138. void RegisterStyle (Style baseStyle, Style linkStyle) {
  1139. linkStyle.CopyTextStylesFrom (baseStyle);
  1140. linkStyle.BorderStyle = BorderStyle.None;
  1141. baseStyle.Font.Reset ();
  1142. RegisterStyle (linkStyle);
  1143. RegisterStyle (baseStyle);
  1144. }
  1145. void RegisterStyle (Style baseStyle) {
  1146. if (Page.Header == null)
  1147. return;
  1148. string className = IncrementStyleClassName ().Trim ('_');
  1149. baseStyle.SetRegisteredCssClass (className);
  1150. Page.Header.StyleSheet.CreateStyleRule (baseStyle, this, "." + className);
  1151. }
  1152. string GetBindingKey (string dataMember, int depth)
  1153. {
  1154. return dataMember + " " + depth;
  1155. }
  1156. void InitializeDataBindings () {
  1157. if (dataBindings != null && dataBindings.Count > 0) {
  1158. bindings = new Hashtable ();
  1159. foreach (TreeNodeBinding bin in dataBindings) {
  1160. string key = GetBindingKey (bin.DataMember, bin.Depth);
  1161. if (!bindings.ContainsKey(key))
  1162. bindings [key] = bin;
  1163. }
  1164. }
  1165. else
  1166. bindings = null;
  1167. }
  1168. internal TreeNodeBinding FindBindingForNode (string type, int depth)
  1169. {
  1170. if (bindings == null)
  1171. return null;
  1172. TreeNodeBinding bin = (TreeNodeBinding) bindings [GetBindingKey (type, depth)];
  1173. if (bin != null) return bin;
  1174. bin = (TreeNodeBinding) bindings [GetBindingKey (type, -1)];
  1175. if (bin != null) return bin;
  1176. bin = (TreeNodeBinding) bindings [GetBindingKey ("", depth)];
  1177. if (bin != null) return bin;
  1178. return (TreeNodeBinding) bindings [GetBindingKey ("", -1)];
  1179. }
  1180. internal void DecorateNode(TreeNode node)
  1181. {
  1182. if (node == null)
  1183. return;
  1184. if (node.ImageUrl != null && node.ImageUrl.Length > 0)
  1185. return;
  1186. if (node.IsRootNode && rootNodeStyle != null) {
  1187. node.ImageUrl = rootNodeStyle.ImageUrl;
  1188. return;
  1189. }
  1190. if (node.IsParentNode && parentNodeStyle != null) {
  1191. node.ImageUrl = parentNodeStyle.ImageUrl;
  1192. return;
  1193. }
  1194. if (node.IsLeafNode && leafNodeStyle != null)
  1195. node.ImageUrl = leafNodeStyle.ImageUrl;
  1196. }
  1197. protected internal override void RenderContents (HtmlTextWriter writer)
  1198. {
  1199. SiteMapDataSource siteMap = GetDataSource () as SiteMapDataSource;
  1200. bool checkSitePath = IsBoundUsingDataSourceID && siteMap != null;
  1201. if (checkSitePath) {
  1202. IHierarchyData data = siteMap.Provider.CurrentNode;
  1203. if (data != null)
  1204. activeSiteMapPath = data.Path;
  1205. }
  1206. ArrayList levelLines = new ArrayList ();
  1207. int num = Nodes.Count;
  1208. for (int n=0; n<num; n++)
  1209. RenderNode (writer, Nodes [n], 0, levelLines, n>0, n<num-1);
  1210. }
  1211. protected override void AddAttributesToRender(HtmlTextWriter writer)
  1212. {
  1213. base.AddAttributesToRender (writer);
  1214. }
  1215. public override void RenderBeginTag (HtmlTextWriter writer)
  1216. {
  1217. if (SkipLinkText != "") {
  1218. writer.AddAttribute (HtmlTextWriterAttribute.Href, "#" + ClientID + "_SkipLink");
  1219. writer.RenderBeginTag (HtmlTextWriterTag.A);
  1220. Image img = new Image ();
  1221. ClientScriptManager csm = new ClientScriptManager (null);
  1222. img.ImageUrl = csm.GetWebResourceUrl (typeof (SiteMapPath), "transparent.gif");
  1223. img.Attributes.Add ("height", "0");
  1224. img.Attributes.Add ("width", "0");
  1225. img.AlternateText = SkipLinkText;
  1226. img.Render (writer);
  1227. writer.RenderEndTag ();
  1228. }
  1229. base.RenderBeginTag (writer);
  1230. }
  1231. public override void RenderEndTag (HtmlTextWriter writer)
  1232. {
  1233. base.RenderEndTag (writer);
  1234. if (SkipLinkText != "") {
  1235. writer.AddAttribute (HtmlTextWriterAttribute.Id, ClientID + "_SkipLink");
  1236. writer.RenderBeginTag (HtmlTextWriterTag.A);
  1237. writer.RenderEndTag ();
  1238. }
  1239. }
  1240. void RenderNode (HtmlTextWriter writer, TreeNode node, int level, ArrayList levelLines, bool hasPrevious, bool hasNext)
  1241. {
  1242. DecorateNode(node);
  1243. string nodeImage;
  1244. bool clientExpand = EnableClientScript && Events [TreeNodeCollapsedEvent] == null && Events [TreeNodeExpandedEvent] == null;
  1245. ImageStyle imageStyle = GetImageStyle ();
  1246. bool renderChildNodes = node.Expanded.HasValue && node.Expanded.Value;
  1247. if (clientExpand && !renderChildNodes)
  1248. renderChildNodes = (!node.PopulateOnDemand || node.Populated);
  1249. bool hasChildNodes;
  1250. if (renderChildNodes)
  1251. hasChildNodes = node.ChildNodes.Count > 0;
  1252. else
  1253. hasChildNodes = (node.PopulateOnDemand && !node.Populated) || node.ChildNodes.Count > 0;
  1254. writer.AddAttribute ("cellpadding", "0", false);
  1255. writer.AddAttribute ("cellspacing", "0", false);
  1256. writer.AddStyleAttribute ("border-width", "0");
  1257. writer.RenderBeginTag (HtmlTextWriterTag.Table);
  1258. Unit nodeSpacing = GetNodeSpacing (node);
  1259. if (nodeSpacing != Unit.Empty && (node.Depth > 0 || node.Index > 0))
  1260. RenderMenuItemSpacing (writer, nodeSpacing);
  1261. writer.RenderBeginTag (HtmlTextWriterTag.Tr);
  1262. // Vertical lines from previous levels
  1263. nodeImage = GetNodeImageUrl ("i", imageStyle);
  1264. for (int n=0; n<level; n++) {
  1265. writer.RenderBeginTag (HtmlTextWriterTag.Td);
  1266. writer.AddStyleAttribute ("width", NodeIndent + "px");
  1267. writer.AddStyleAttribute ("height", "1px");
  1268. writer.RenderBeginTag (HtmlTextWriterTag.Div);
  1269. if (ShowLines && levelLines [n] != null) {
  1270. writer.AddAttribute ("src", nodeImage);
  1271. writer.AddAttribute (HtmlTextWriterAttribute.Alt, "", false);
  1272. writer.RenderBeginTag (HtmlTextWriterTag.Img);
  1273. writer.RenderEndTag ();
  1274. }
  1275. writer.RenderEndTag ();
  1276. writer.RenderEndTag (); // TD
  1277. }
  1278. // Node image + line
  1279. if (ShowExpandCollapse || ShowLines) {
  1280. bool buttonImage = false;
  1281. string tooltip = "";
  1282. string shape = "";
  1283. if (ShowLines) {
  1284. if (hasPrevious && hasNext) shape = "t";
  1285. else if (hasPrevious && !hasNext) shape = "l";
  1286. else if (!hasPrevious && hasNext) shape = "r";
  1287. else shape = "dash";
  1288. }
  1289. if (ShowExpandCollapse) {
  1290. if (hasChildNodes) {
  1291. buttonImage = true;
  1292. if (node.Expanded.HasValue && node.Expanded.Value) shape += "minus";
  1293. else shape += "plus";
  1294. tooltip = GetNodeImageToolTip (!(node.Expanded.HasValue && node.Expanded.Value), node.Text);
  1295. } else if (!ShowLines)
  1296. shape = "noexpand";
  1297. }
  1298. if (shape != "") {
  1299. nodeImage = GetNodeImageUrl (shape, imageStyle);
  1300. writer.RenderBeginTag (HtmlTextWriterTag.Td); // TD
  1301. if (buttonImage) {
  1302. if (!clientExpand || (!PopulateNodesFromClient && node.PopulateOnDemand && !node.Populated))
  1303. writer.AddAttribute ("href", GetClientEvent (node, "ec"));
  1304. else
  1305. writer.AddAttribute ("href", GetClientExpandEvent(node));
  1306. writer.RenderBeginTag (HtmlTextWriterTag.A); // Anchor
  1307. }
  1308. // tooltip is 'HtmlAttributeEncoded'
  1309. writer.AddAttribute ("alt", tooltip);
  1310. if (buttonImage && clientExpand)
  1311. writer.AddAttribute ("id", GetNodeClientId (node, "img"));
  1312. writer.AddAttribute ("src", nodeImage);
  1313. if (buttonImage)
  1314. writer.AddStyleAttribute (HtmlTextWriterStyle.BorderWidth, "0");
  1315. writer.RenderBeginTag (HtmlTextWriterTag.Img);
  1316. writer.RenderEndTag ();
  1317. if (buttonImage)
  1318. writer.RenderEndTag (); // Anchor
  1319. writer.RenderEndTag (); // TD
  1320. }
  1321. }
  1322. // Node icon
  1323. string imageUrl = node.ImageUrl.Length > 0 ? ResolveClientUrl (node.ImageUrl) : null;
  1324. if (String.IsNullOrEmpty (imageUrl) && imageStyle != null) {
  1325. if (imageStyle.RootIcon != null && node.IsRootNode)
  1326. imageUrl = GetNodeIconUrl (imageStyle.RootIcon);
  1327. else if (imageStyle.ParentIcon != null && node.IsParentNode)
  1328. imageUrl = GetNodeIconUrl (imageStyle.ParentIcon);
  1329. else if (imageStyle.LeafIcon != null && node.IsLeafNode)
  1330. imageUrl = GetNodeIconUrl (imageStyle.LeafIcon);
  1331. }
  1332. if (level < LevelStyles.Count && LevelStyles [level].ImageUrl != null)
  1333. imageUrl = ResolveClientUrl (LevelStyles [level].ImageUrl);
  1334. if (!String.IsNullOrEmpty (imageUrl)) {
  1335. writer.RenderBeginTag (HtmlTextWriterTag.Td); // TD
  1336. BeginNodeTag (writer, node, clientExpand);
  1337. writer.AddAttribute ("src", imageUrl);
  1338. writer.AddStyleAttribute (HtmlTextWriterStyle.BorderWidth, "0");
  1339. writer.AddAttribute ("alt", node.ImageToolTip);
  1340. writer.RenderBeginTag (HtmlTextWriterTag.Img);
  1341. writer.RenderEndTag (); // IMG
  1342. writer.RenderEndTag (); // style tag
  1343. writer.RenderEndTag (); // TD
  1344. }
  1345. if (!NodeWrap)
  1346. writer.AddStyleAttribute ("white-space", "nowrap");
  1347. bool nodeIsSelected = node == SelectedNode && selectedNodeStyle != null;
  1348. if (!nodeIsSelected && selectedNodeStyle != null) {
  1349. if (!String.IsNullOrEmpty (activeSiteMapPath))
  1350. nodeIsSelected = String.Compare (activeSiteMapPath,
  1351. node.NavigateUrl,
  1352. HttpRuntime.CaseInsensitive ? StringComparison.OrdinalIgnoreCase : StringComparison.Ordinal) == 0;
  1353. }
  1354. AddNodeStyle (writer, node, level, nodeIsSelected);
  1355. if (EnableClientScript) {
  1356. writer.AddAttribute ("onmouseout", "TreeView_UnhoverNode(this)", false);
  1357. writer.AddAttribute ("onmouseover", "TreeView_HoverNode('" + ClientID + "', this)");
  1358. }
  1359. writer.RenderBeginTag (HtmlTextWriterTag.Td); // TD
  1360. // Checkbox
  1361. if (node.ShowCheckBoxInternal) {
  1362. writer.AddAttribute ("name", ClientID + "_cs_" + node.Path);
  1363. writer.AddAttribute ("type", "checkbox", false);
  1364. writer.AddAttribute ("title", node.Text);
  1365. if (node.Checked) writer.AddAttribute ("checked", "checked", false);
  1366. writer.RenderBeginTag (HtmlTextWriterTag.Input); // INPUT
  1367. writer.RenderEndTag (); // INPUT
  1368. }
  1369. // Text
  1370. node.BeginRenderText (writer);
  1371. if (clientExpand)
  1372. writer.AddAttribute ("id", GetNodeClientId (node, "txt"));
  1373. AddNodeLinkStyle (writer, node, level, nodeIsSelected);
  1374. BeginNodeTag (writer, node, clientExpand);
  1375. writer.Write (node.Text);
  1376. writer.RenderEndTag (); // style tag
  1377. node.EndRenderText (writer);
  1378. writer.RenderEndTag (); // TD
  1379. writer.RenderEndTag (); // TR
  1380. if (nodeSpacing != Unit.Empty)
  1381. RenderMenuItemSpacing (writer, nodeSpacing);
  1382. writer.RenderEndTag (); // TABLE
  1383. // Children
  1384. if (hasChildNodes) {
  1385. if (level >= levelLines.Count) {
  1386. if (hasNext)
  1387. levelLines.Add (this);
  1388. else
  1389. levelLines.Add (null);
  1390. } else {
  1391. if (hasNext)
  1392. levelLines [level] = this;
  1393. else
  1394. levelLines [level] = null;
  1395. }
  1396. if (clientExpand) {
  1397. if (!(node.Expanded.HasValue && node.Expanded.Value))
  1398. writer.AddStyleAttribute ("display", "none");
  1399. else
  1400. writer.AddStyleAttribute ("display", "block");
  1401. writer.AddAttribute ("id", GetNodeClientId (node, null));
  1402. writer.RenderBeginTag (HtmlTextWriterTag.Span);
  1403. if (renderChildNodes) {
  1404. AddChildrenPadding (writer, node);
  1405. int num = node.ChildNodes.Count;
  1406. for (int n=0; n<num; n++)
  1407. RenderNode (writer, node.ChildNodes [n], level + 1, levelLines, true, n<num-1);
  1408. if (hasNext)
  1409. AddChildrenPadding (writer, node);
  1410. }
  1411. writer.RenderEndTag (); // SPAN
  1412. } else if (renderChildNodes) {
  1413. AddChildrenPadding (writer, node);
  1414. int num = node.ChildNodes.Count;
  1415. for (int n=0; n<num; n++)
  1416. RenderNode (writer, node.ChildNodes [n], level + 1, levelLines, true, n<num-1);
  1417. if (hasNext)
  1418. AddChildrenPadding (writer, node);
  1419. }
  1420. }
  1421. }
  1422. void AddChildrenPadding (HtmlTextWriter writer, TreeNode node)
  1423. {
  1424. int level = node.Depth;
  1425. Unit cnp = Unit.Empty;
  1426. if (levelStyles != null && level < levelStyles.Count)
  1427. cnp = levelStyles [level].ChildNodesPadding;
  1428. if (cnp.IsEmpty && nodeStyle != null)
  1429. cnp = nodeStyle.ChildNodesPadding;
  1430. double value;
  1431. if (cnp.IsEmpty || (value = cnp.Value) == 0 || cnp.Type != UnitType.Pixel)
  1432. return;
  1433. writer.RenderBeginTag (HtmlTextWriterTag.Table);
  1434. writer.AddAttribute ("height", ((int) value).ToString (), false);
  1435. writer.RenderBeginTag (HtmlTextWriterTag.Tr);
  1436. writer.RenderBeginTag (HtmlTextWriterTag.Td);
  1437. writer.RenderEndTag (); // td
  1438. writer.RenderEndTag (); // tr
  1439. writer.RenderEndTag (); // table
  1440. }
  1441. void RenderMenuItemSpacing (HtmlTextWriter writer, Unit itemSpacing) {
  1442. writer.AddStyleAttribute ("height", itemSpacing.ToString ());
  1443. writer.RenderBeginTag (HtmlTextWriterTag.Tr);
  1444. writer.RenderBeginTag (HtmlTextWriterTag.Td);
  1445. writer.RenderEndTag ();
  1446. writer.RenderEndTag ();
  1447. }
  1448. Unit GetNodeSpacing (TreeNode node) {
  1449. if (node.Selected && selectedNodeStyle != null && selectedNodeStyle.NodeSpacing != Unit.Empty) {
  1450. return selectedNodeStyle.NodeSpacing;
  1451. }
  1452. if (levelStyles != null && node.Depth < levelStyles.Count && levelStyles [node.Depth].NodeSpacing != Unit.Empty) {
  1453. return levelStyles [node.Depth].NodeSpacing;
  1454. }
  1455. if (node.IsLeafNode) {
  1456. if (leafNodeStyle != null && leafNodeStyle.NodeSpacing != Unit.Empty)
  1457. return leafNodeStyle.NodeSpacing;
  1458. }
  1459. else if (node.IsRootNode) {
  1460. if (rootNodeStyle != null && rootNodeStyle.NodeSpacing != Unit.Empty)
  1461. return rootNodeStyle.NodeSpacing;
  1462. }
  1463. else if (node.IsParentNode) {
  1464. if (parentNodeStyle != null && parentNodeStyle.NodeSpacing != Unit.Empty)
  1465. return parentNodeStyle.NodeSpacing;
  1466. }
  1467. if (nodeStyle != null)
  1468. return nodeStyle.NodeSpacing;
  1469. else
  1470. return Unit.Empty;
  1471. }
  1472. void AddNodeStyle (HtmlTextWriter writer, TreeNode node, int level, bool nodeIsSelected)
  1473. {
  1474. TreeNodeStyle style = new TreeNodeStyle ();
  1475. if (Page.Header != null) {
  1476. // styles are registered
  1477. if (nodeStyle != null) {
  1478. style.AddCssClass (nodeStyle.CssClass);
  1479. style.AddCssClass (nodeStyle.RegisteredCssClass);
  1480. }
  1481. if (node.IsLeafNode) {
  1482. if (leafNodeStyle != null) {
  1483. style.AddCssClass (leafNodeStyle.CssClass);
  1484. style.AddCssClass (leafNodeStyle.RegisteredCssClass);
  1485. }
  1486. } else if (node.IsRootNode) {
  1487. if (rootNodeStyle != null) {
  1488. style.AddCssClass (rootNodeStyle.CssClass);
  1489. style.AddCssClass (rootNodeStyle.RegisteredCssClass);
  1490. }
  1491. } else if (node.IsParentNode) {
  1492. if (parentNodeStyle != null) {
  1493. style.AddCssClass (parentNodeStyle.CssClass);
  1494. style.AddCssClass (parentNodeStyle.RegisteredCssClass);
  1495. }
  1496. }
  1497. if (levelStyles != null && levelStyles.Count > level) {
  1498. style.AddCssClass (levelStyles [level].CssClass);
  1499. style.AddCssClass (levelStyles [level].RegisteredCssClass);
  1500. }
  1501. if (nodeIsSelected) {
  1502. style.AddCssClass (selectedNodeStyle.CssClass);
  1503. style.AddCssClass (selectedNodeStyle.RegisteredCssClass);
  1504. }
  1505. } else {
  1506. // styles are not registered
  1507. if (nodeStyle != null) {
  1508. style.CopyFrom (nodeStyle);
  1509. }
  1510. if (node.IsLeafNode) {
  1511. if (leafNodeStyle != null) {
  1512. style.CopyFrom (leafNodeStyle);
  1513. }
  1514. }
  1515. else if (node.IsRootNode) {
  1516. if (rootNodeStyle != null) {
  1517. style.CopyFrom (rootNodeStyle);
  1518. }
  1519. }
  1520. else if (node.IsParentNode) {
  1521. if (parentNodeStyle != null) {
  1522. style.CopyFrom (parentNodeStyle);
  1523. }
  1524. }
  1525. if (levelStyles != null && levelStyles.Count > level) {
  1526. style.CopyFrom (levelStyles [level]);
  1527. }
  1528. if (nodeIsSelected) {
  1529. style.CopyFrom (selectedNodeStyle);
  1530. }
  1531. }
  1532. style.AddAttributesToRender (writer);
  1533. }
  1534. void AddNodeLinkStyle (HtmlTextWriter writer, TreeNode node, int level, bool nodeIsSelected)
  1535. {
  1536. Style style = new Style ();
  1537. if (Page.Header != null) {
  1538. // styles are registered
  1539. style.AddCssClass (ControlLinkStyle.RegisteredCssClass);
  1540. if (nodeStyle != null) {
  1541. style.AddCssClass (nodeLinkStyle.CssClass);
  1542. style.AddCssClass (nodeLinkStyle.RegisteredCssClass);
  1543. }
  1544. if (node.IsLeafNode) {
  1545. if (leafNodeStyle != null) {
  1546. style.AddCssClass (leafNodeLinkStyle.CssClass);
  1547. style.AddCssClass (leafNodeLinkStyle.RegisteredCssClass);
  1548. }
  1549. }
  1550. else if (node.IsRootNode) {
  1551. if (rootNodeStyle != null) {
  1552. style.AddCssClass (rootNodeLinkStyle.CssClass);
  1553. style.AddCssClass (rootNodeLinkStyle.RegisteredCssClass);
  1554. }
  1555. }
  1556. else if (node.IsParentNode) {
  1557. if (parentNodeStyle != null) {
  1558. style.AddCssClass (parentNodeLinkStyle.CssClass);
  1559. style.AddCssClass (parentNodeLinkStyle.RegisteredCssClass);
  1560. }
  1561. }
  1562. if (levelStyles != null && levelStyles.Count > level) {
  1563. style.AddCssClass (levelLinkStyles [level].CssClass);
  1564. style.AddCssClass (levelLinkStyles [level].RegisteredCssClass);
  1565. }
  1566. if (nodeIsSelected) {
  1567. style.AddCssClass (selectedNodeLinkStyle.CssClass);
  1568. style.AddCssClass (selectedNodeLinkStyle.RegisteredCssClass);
  1569. }
  1570. }
  1571. else {
  1572. // styles are not registered
  1573. style.CopyFrom (ControlLinkStyle);
  1574. if (nodeStyle != null) {
  1575. style.CopyFrom (nodeLinkStyle);
  1576. }
  1577. if (node.IsLeafNode) {
  1578. if (node.IsLeafNode && leafNodeStyle != null) {
  1579. style.CopyFrom (leafNodeLinkStyle);
  1580. }
  1581. }
  1582. else if (node.IsRootNode) {
  1583. if (node.IsRootNode && rootNodeStyle != null) {
  1584. style.CopyFrom (rootNodeLinkStyle);
  1585. }
  1586. }
  1587. else if (node.IsParentNode) {
  1588. if (node.IsParentNode && parentNodeStyle != null) {
  1589. style.CopyFrom (parentNodeLinkStyle);
  1590. }
  1591. }
  1592. if (levelStyles != null && levelStyles.Count > level) {
  1593. style.CopyFrom (levelLinkStyles [level]);
  1594. }
  1595. if (nodeIsSelected) {
  1596. style.CopyFrom (selectedNodeLinkStyle);
  1597. }
  1598. style.AlwaysRenderTextDecoration = true;
  1599. }
  1600. style.AddAttributesToRender (writer);
  1601. }
  1602. void BeginNodeTag (HtmlTextWriter writer, TreeNode node, bool clientExpand)
  1603. {
  1604. if(node.ToolTip.Length>0)
  1605. writer.AddAttribute ("title", node.ToolTip);
  1606. if (node.NavigateUrl != "") {
  1607. string target = node.Target.Length > 0 ? node.Target : Target;
  1608. #if TARGET_J2EE
  1609. string navUrl = ResolveClientUrl (node.NavigateUrl, String.Compare (target, "_blank", StringComparison.InvariantCultureIgnoreCase) != 0);
  1610. #else
  1611. string navUrl = ResolveClientUrl (node.NavigateUrl);
  1612. #endif
  1613. writer.AddAttribute ("href", navUrl);
  1614. if (target.Length > 0)
  1615. writer.AddAttribute ("target", target);
  1616. writer.RenderBeginTag (HtmlTextWriterTag.A);
  1617. }
  1618. else if (node.SelectAction != TreeNodeSelectAction.None) {
  1619. if (node.SelectAction == TreeNodeSelectAction.Expand && clientExpand)
  1620. writer.AddAttribute ("href", GetClientExpandEvent (node));
  1621. else
  1622. writer.AddAttribute ("href", GetClientEvent (node, "sel"));
  1623. writer.RenderBeginTag (HtmlTextWriterTag.A);
  1624. }
  1625. else
  1626. writer.RenderBeginTag (HtmlTextWriterTag.Span);
  1627. }
  1628. string GetNodeImageToolTip (bool expand, string txt) {
  1629. if (expand) {
  1630. if (ExpandImageToolTip != "")
  1631. return String.Format (ExpandImageToolTip, HttpUtility.HtmlAttributeEncode (txt));
  1632. else if (txt != null)
  1633. return "Expand " + HttpUtility.HtmlAttributeEncode (txt);
  1634. else
  1635. return "Expand {0}";
  1636. } else {
  1637. if (CollapseImageToolTip != "")
  1638. return String.Format (CollapseImageToolTip, HttpUtility.HtmlAttributeEncode (txt));
  1639. else if (txt != null)
  1640. return "Collapse " + HttpUtility.HtmlAttributeEncode (txt);
  1641. else
  1642. return "Collapse {0}";
  1643. }
  1644. }
  1645. string GetNodeClientId (TreeNode node, string sufix)
  1646. {
  1647. return ClientID + "_" + node.Path + (sufix != null ? "_" + sufix : "");
  1648. }
  1649. string GetNodeImageUrl (string shape, ImageStyle imageStyle)
  1650. {
  1651. if (ShowLines) {
  1652. if (!String.IsNullOrEmpty (LineImagesFolder))
  1653. return ResolveClientUrl (LineImagesFolder + "/" + shape + ".gif");
  1654. } else {
  1655. if (imageStyle != null) {
  1656. if (shape == "plus") {
  1657. if (!String.IsNullOrEmpty (imageStyle.Expand))
  1658. return GetNodeIconUrl (imageStyle.Expand);
  1659. }
  1660. else if (shape == "minus") {
  1661. if (!String.IsNullOrEmpty (imageStyle.Collapse))
  1662. return GetNodeIconUrl (imageStyle.Collapse);
  1663. }
  1664. else if (shape == "noexpand") {
  1665. if (!String.IsNullOrEmpty (imageStyle.NoExpand))
  1666. return GetNodeIconUrl (imageStyle.NoExpand);
  1667. }
  1668. }
  1669. else {
  1670. if (shape == "plus") {
  1671. if (!String.IsNullOrEmpty (ExpandImageUrl))
  1672. return ResolveClientUrl (ExpandImageUrl);
  1673. }
  1674. else if (shape == "minus") {
  1675. if (!String.IsNullOrEmpty (CollapseImageUrl))
  1676. return ResolveClientUrl (CollapseImageUrl);
  1677. }
  1678. else if (shape == "noexpand") {
  1679. if (!String.IsNullOrEmpty (NoExpandImageUrl))
  1680. return ResolveClientUrl (NoExpandImageUrl);
  1681. }
  1682. }
  1683. if (!String.IsNullOrEmpty (LineImagesFolder))
  1684. return ResolveClientUrl (LineImagesFolder + "/" + shape + ".gif");
  1685. }
  1686. return Page.ClientScript.GetWebResourceUrl (typeof (TreeView), "TreeView_" + shape + ".gif");
  1687. }
  1688. string GetNodeIconUrl (string icon)
  1689. {
  1690. return Page.ClientScript.GetWebResourceUrl (typeof (TreeView), icon + ".gif");
  1691. }
  1692. string GetClientEvent (TreeNode node, string ev)
  1693. {
  1694. return Page.ClientScript.GetPostBackClientHyperlink (this, ev + "|" + node.Path, true);
  1695. }
  1696. string GetClientExpandEvent (TreeNode node)
  1697. {
  1698. return String.Format ("javascript:TreeView_ToggleExpand ('{0}','{1}','{2}','{3}','{4}','{5}')",
  1699. ClientID,
  1700. node.Path,
  1701. HttpUtility.HtmlAttributeEncode (node.Value).Replace ("'", "\\'").Replace ("|","U+007C"),
  1702. HttpUtility.HtmlAttributeEncode (node.ImageUrl).Replace ("'", "\\'").Replace ("|","U+007c"),
  1703. HttpUtility.HtmlAttributeEncode (node.NavigateUrl).Replace ("'", "\\'").Replace ("|","U+007C"),
  1704. HttpUtility.HtmlAttributeEncode (node.Target).Replace ("'", "\\'").Replace ("|","U+007C"));
  1705. }
  1706. TreeNode FindNodeByPos (string path)
  1707. {
  1708. string[] indexes = path.Split ('_');
  1709. TreeNode node = null;
  1710. foreach (string index in indexes) {
  1711. int i = int.Parse (index);
  1712. if (node == null) {
  1713. if (i >= Nodes.Count) return null;
  1714. node = Nodes [i];
  1715. } else {
  1716. if (i >= node.ChildNodes.Count) return null;
  1717. node = node.ChildNodes [i];
  1718. }
  1719. }
  1720. return node;
  1721. }
  1722. void UnsetCheckStates (TreeNodeCollection col, NameValueCollection states)
  1723. {
  1724. foreach (TreeNode node in col) {
  1725. if (node.ShowCheckBoxInternal && node.Checked) {
  1726. if (states == null || states [ClientID + "_cs_" + node.Path] == null)
  1727. node.Checked = false;
  1728. }
  1729. if (node.HasChildData)
  1730. UnsetCheckStates (node.ChildNodes, states);
  1731. }
  1732. }
  1733. void SetCheckStates (NameValueCollection states)
  1734. {
  1735. if (states == null)
  1736. return;
  1737. string keyPrefix = ClientID + "_cs_";
  1738. foreach (string key in states) {
  1739. if (key.StartsWith (keyPrefix, StringComparison.Ordinal)) {
  1740. string id = key.Substring (keyPrefix.Length);
  1741. TreeNode node = FindNodeByPos (id);
  1742. if (node != null && !node.Checked)
  1743. node.Checked = true;
  1744. }
  1745. }
  1746. }
  1747. void UnsetExpandStates (TreeNodeCollection col, string[] states)
  1748. {
  1749. foreach (TreeNode node in col) {
  1750. if (node.Expanded.HasValue && node.Expanded.Value) {
  1751. bool expand = (Array.IndexOf (states, node.Path) != -1);
  1752. if (!expand) node.Expanded = false;
  1753. }
  1754. if (node.HasChildData)
  1755. UnsetExpandStates (node.ChildNodes, states);
  1756. }
  1757. }
  1758. void SetExpandStates (string[] states)
  1759. {
  1760. foreach (string id in states) {
  1761. if (id == null || id == "") continue;
  1762. TreeNode node = FindNodeByPos (id);
  1763. if (node != null)
  1764. node.Expanded = true;
  1765. }
  1766. }
  1767. string GetExpandStates ()
  1768. {
  1769. StringBuilder sb = new StringBuilder ("|");
  1770. foreach (TreeNode node in Nodes)
  1771. GetExpandStates (sb, node);
  1772. return sb.ToString ();
  1773. }
  1774. void GetExpandStates (StringBuilder sb, TreeNode node)
  1775. {
  1776. if (node.Expanded.HasValue && node.Expanded.Value) {
  1777. sb.Append (node.Path);
  1778. sb.Append ('|');
  1779. }
  1780. if (node.HasChildData) {
  1781. foreach (TreeNode child in node.ChildNodes)
  1782. GetExpandStates (sb, child);
  1783. }
  1784. }
  1785. }
  1786. }
  1787. #endif