Code:
/ Dotnetfx_Win7_3.5.1 / Dotnetfx_Win7_3.5.1 / 3.5.1 / DEVDIV / depot / DevDiv / releases / whidbey / NetFXspW7 / ndp / fx / src / xsp / System / Web / UI / HTMLTextWriter.cs / 1 / HTMLTextWriter.cs
//------------------------------------------------------------------------------ //// Copyright (c) Microsoft Corporation. All rights reserved. // //----------------------------------------------------------------------------- // HtmlTextWriter.cs // namespace System.Web.UI { using System; using System.Collections; using System.Collections.Specialized; using System.IO; using System.Text; using System.Globalization; using System.Security.Permissions; using System.Web.UI.WebControls; using System.Web.Util; [AspNetHostingPermission(SecurityAction.LinkDemand, Level=AspNetHostingPermissionLevel.Minimal)] [AspNetHostingPermission(SecurityAction.InheritanceDemand, Level=AspNetHostingPermissionLevel.Minimal)] public class HtmlTextWriter : TextWriter { private Layout _currentLayout = new Layout(HorizontalAlign.NotSet, true /* wrap */); private Layout _currentWrittenLayout = null; internal virtual bool RenderDivAroundHiddenInputs { get { return true; } } #if SHIPPINGADAPTERS internal void CloseDiv(){ WriteEndTag("div"); } #endif public virtual void EnterStyle(Style style, HtmlTextWriterTag tag) { if (!style.IsEmpty || tag != HtmlTextWriterTag.Span) { style.AddAttributesToRender(this); RenderBeginTag(tag); } } public virtual void ExitStyle(System.Web.UI.WebControls.Style style, HtmlTextWriterTag tag) { // Review: This requires that the style doesn't change between beginstyle/endstyle. if (!style.IsEmpty || tag != HtmlTextWriterTag.Span) { RenderEndTag(); } } internal virtual void OpenDiv() { OpenDiv(_currentLayout, (_currentLayout != null) && (_currentLayout.Align != HorizontalAlign.NotSet), (_currentLayout != null) && !_currentLayout.Wrap); } private void OpenDiv(Layout layout, bool writeHorizontalAlign, bool writeWrapping) { WriteBeginTag("div"); if (writeHorizontalAlign) { String alignment; switch (layout.Align) { case HorizontalAlign.Right: alignment = "text-align:right"; break; case HorizontalAlign.Center: alignment = "text-align:center"; break; default: alignment = "text-align:left"; break; } WriteAttribute("style", alignment); } if (writeWrapping) { WriteAttribute("mode", layout.Wrap == true ? "wrap" : "nowrap"); } Write('>'); _currentWrittenLayout = layout; } public virtual bool IsValidFormAttribute(String attribute) { return true; } private TextWriter writer; private int indentLevel; private bool tabsPending; private string tabString; public const char TagLeftChar = '<'; public const char TagRightChar = '>'; public const string SelfClosingChars = " /"; public const string SelfClosingTagEnd = " />"; public const string EndTagLeftChars = ""; public const char DoubleQuoteChar = '"'; public const char SingleQuoteChar = '\''; public const char SpaceChar = ' '; public const char EqualsChar = '='; public const char SlashChar = '/'; public const string EqualsDoubleQuoteString = "=\""; public const char SemicolonChar = ';'; public const char StyleEqualsChar = ':'; public const string DefaultTabString = "\t"; // The DesignerRegion attribute name must be kept in [....] with // System.Web.UI.Design.DesignerRegion.DesignerRegionNameAttribute internal const string DesignerRegionAttributeName = "_designerRegion"; private static Hashtable _tagKeyLookupTable; private static Hashtable _attrKeyLookupTable; private static TagInformation[] _tagNameLookupArray; private static AttributeInformation[] _attrNameLookupArray; private RenderAttribute[] _attrList; private int _attrCount; private int _endTagCount; private TagStackEntry[] _endTags; private HttpWriter _httpWriter; private int _inlineCount; private bool _isDescendant; private RenderStyle[] _styleList; private int _styleCount; private int _tagIndex; private HtmlTextWriterTag _tagKey; private string _tagName; static HtmlTextWriter() { // register known tags _tagKeyLookupTable = new Hashtable((int)HtmlTextWriterTag.Xml + 1); _tagNameLookupArray = new TagInformation[(int)HtmlTextWriterTag.Xml + 1]; RegisterTag(String.Empty, HtmlTextWriterTag.Unknown, TagType.Other); RegisterTag("a", HtmlTextWriterTag.A, TagType.Inline); RegisterTag("acronym", HtmlTextWriterTag.Acronym, TagType.Inline); RegisterTag("address", HtmlTextWriterTag.Address, TagType.Other); RegisterTag("area", HtmlTextWriterTag.Area, TagType.NonClosing); RegisterTag("b", HtmlTextWriterTag.B, TagType.Inline); RegisterTag("base", HtmlTextWriterTag.Base, TagType.NonClosing); RegisterTag("basefont", HtmlTextWriterTag.Basefont, TagType.NonClosing); RegisterTag("bdo", HtmlTextWriterTag.Bdo, TagType.Inline); RegisterTag("bgsound", HtmlTextWriterTag.Bgsound, TagType.NonClosing); RegisterTag("big", HtmlTextWriterTag.Big, TagType.Inline); RegisterTag("blockquote", HtmlTextWriterTag.Blockquote, TagType.Other); RegisterTag("body", HtmlTextWriterTag.Body, TagType.Other); RegisterTag("br", HtmlTextWriterTag.Br, TagType.Other); RegisterTag("button", HtmlTextWriterTag.Button, TagType.Inline); RegisterTag("caption", HtmlTextWriterTag.Caption, TagType.Other); RegisterTag("center", HtmlTextWriterTag.Center, TagType.Other); RegisterTag("cite", HtmlTextWriterTag.Cite, TagType.Inline); RegisterTag("code", HtmlTextWriterTag.Code, TagType.Inline); RegisterTag("col", HtmlTextWriterTag.Col, TagType.NonClosing); RegisterTag("colgroup", HtmlTextWriterTag.Colgroup, TagType.Other); RegisterTag("del", HtmlTextWriterTag.Del, TagType.Inline); RegisterTag("dd", HtmlTextWriterTag.Dd, TagType.Inline); RegisterTag("dfn", HtmlTextWriterTag.Dfn, TagType.Inline); RegisterTag("dir", HtmlTextWriterTag.Dir, TagType.Other); RegisterTag("div", HtmlTextWriterTag.Div, TagType.Other); RegisterTag("dl", HtmlTextWriterTag.Dl, TagType.Other); RegisterTag("dt", HtmlTextWriterTag.Dt, TagType.Inline); RegisterTag("em", HtmlTextWriterTag.Em, TagType.Inline); RegisterTag("embed", HtmlTextWriterTag.Embed, TagType.NonClosing); RegisterTag("fieldset", HtmlTextWriterTag.Fieldset, TagType.Other); RegisterTag("font", HtmlTextWriterTag.Font, TagType.Inline); RegisterTag("form", HtmlTextWriterTag.Form, TagType.Other); RegisterTag("frame", HtmlTextWriterTag.Frame, TagType.NonClosing); RegisterTag("frameset", HtmlTextWriterTag.Frameset, TagType.Other); RegisterTag("h1", HtmlTextWriterTag.H1, TagType.Other); RegisterTag("h2", HtmlTextWriterTag.H2, TagType.Other); RegisterTag("h3", HtmlTextWriterTag.H3, TagType.Other); RegisterTag("h4", HtmlTextWriterTag.H4, TagType.Other); RegisterTag("h5", HtmlTextWriterTag.H5, TagType.Other); RegisterTag("h6", HtmlTextWriterTag.H6, TagType.Other); RegisterTag("head", HtmlTextWriterTag.Head, TagType.Other); RegisterTag("hr", HtmlTextWriterTag.Hr, TagType.NonClosing); RegisterTag("html", HtmlTextWriterTag.Html, TagType.Other); RegisterTag("i", HtmlTextWriterTag.I, TagType.Inline); RegisterTag("iframe", HtmlTextWriterTag.Iframe, TagType.Other); RegisterTag("img", HtmlTextWriterTag.Img, TagType.NonClosing); RegisterTag("input", HtmlTextWriterTag.Input, TagType.NonClosing); RegisterTag("ins", HtmlTextWriterTag.Ins, TagType.Inline); RegisterTag("isindex", HtmlTextWriterTag.Isindex, TagType.NonClosing); RegisterTag("kbd", HtmlTextWriterTag.Kbd, TagType.Inline); RegisterTag("label", HtmlTextWriterTag.Label, TagType.Inline); RegisterTag("legend", HtmlTextWriterTag.Legend, TagType.Other); RegisterTag("li", HtmlTextWriterTag.Li, TagType.Inline); RegisterTag("link", HtmlTextWriterTag.Link, TagType.NonClosing); RegisterTag("map", HtmlTextWriterTag.Map, TagType.Other); RegisterTag("marquee", HtmlTextWriterTag.Marquee, TagType.Other); RegisterTag("menu", HtmlTextWriterTag.Menu, TagType.Other); RegisterTag("meta", HtmlTextWriterTag.Meta, TagType.NonClosing); RegisterTag("nobr", HtmlTextWriterTag.Nobr, TagType.Inline); RegisterTag("noframes", HtmlTextWriterTag.Noframes, TagType.Other); RegisterTag("noscript", HtmlTextWriterTag.Noscript, TagType.Other); RegisterTag("object", HtmlTextWriterTag.Object, TagType.Other); RegisterTag("ol", HtmlTextWriterTag.Ol, TagType.Other); RegisterTag("option", HtmlTextWriterTag.Option, TagType.Other); RegisterTag("p", HtmlTextWriterTag.P, TagType.Inline); RegisterTag("param", HtmlTextWriterTag.Param, TagType.Other); RegisterTag("pre", HtmlTextWriterTag.Pre, TagType.Other); RegisterTag("ruby", HtmlTextWriterTag.Ruby, TagType.Other); RegisterTag("rt", HtmlTextWriterTag.Rt, TagType.Other); RegisterTag("q", HtmlTextWriterTag.Q, TagType.Inline); RegisterTag("s", HtmlTextWriterTag.S, TagType.Inline); RegisterTag("samp", HtmlTextWriterTag.Samp, TagType.Inline); RegisterTag("script", HtmlTextWriterTag.Script, TagType.Other); RegisterTag("select", HtmlTextWriterTag.Select, TagType.Other); RegisterTag("small", HtmlTextWriterTag.Small, TagType.Other); RegisterTag("span", HtmlTextWriterTag.Span, TagType.Inline); RegisterTag("strike", HtmlTextWriterTag.Strike, TagType.Inline); RegisterTag("strong", HtmlTextWriterTag.Strong, TagType.Inline); RegisterTag("style", HtmlTextWriterTag.Style, TagType.Other); RegisterTag("sub", HtmlTextWriterTag.Sub, TagType.Inline); RegisterTag("sup", HtmlTextWriterTag.Sup, TagType.Inline); RegisterTag("table", HtmlTextWriterTag.Table, TagType.Other); RegisterTag("tbody", HtmlTextWriterTag.Tbody, TagType.Other); RegisterTag("td", HtmlTextWriterTag.Td, TagType.Inline); RegisterTag("textarea", HtmlTextWriterTag.Textarea, TagType.Inline); RegisterTag("tfoot", HtmlTextWriterTag.Tfoot, TagType.Other); RegisterTag("th", HtmlTextWriterTag.Th, TagType.Inline); RegisterTag("thead", HtmlTextWriterTag.Thead, TagType.Other); RegisterTag("title", HtmlTextWriterTag.Title, TagType.Other); RegisterTag("tr", HtmlTextWriterTag.Tr, TagType.Other); RegisterTag("tt", HtmlTextWriterTag.Tt, TagType.Inline); RegisterTag("u", HtmlTextWriterTag.U, TagType.Inline); RegisterTag("ul", HtmlTextWriterTag.Ul, TagType.Other); RegisterTag("var", HtmlTextWriterTag.Var, TagType.Inline); RegisterTag("wbr", HtmlTextWriterTag.Wbr, TagType.NonClosing); RegisterTag("xml", HtmlTextWriterTag.Xml, TagType.Other); // register known attributes _attrKeyLookupTable = new Hashtable((int)HtmlTextWriterAttribute.VCardName + 1); _attrNameLookupArray = new AttributeInformation[(int)HtmlTextWriterAttribute.VCardName + 1]; RegisterAttribute("abbr", HtmlTextWriterAttribute.Abbr, true); RegisterAttribute("accesskey", HtmlTextWriterAttribute.Accesskey, true); RegisterAttribute("align", HtmlTextWriterAttribute.Align, false); RegisterAttribute("alt", HtmlTextWriterAttribute.Alt, true); RegisterAttribute("autocomplete", HtmlTextWriterAttribute.AutoComplete, false); RegisterAttribute("axis", HtmlTextWriterAttribute.Axis, true); RegisterAttribute("background", HtmlTextWriterAttribute.Background, true, true); RegisterAttribute("bgcolor", HtmlTextWriterAttribute.Bgcolor, false); RegisterAttribute("border", HtmlTextWriterAttribute.Border, false); RegisterAttribute("bordercolor", HtmlTextWriterAttribute.Bordercolor, false); RegisterAttribute("cellpadding", HtmlTextWriterAttribute.Cellpadding, false); RegisterAttribute("cellspacing", HtmlTextWriterAttribute.Cellspacing, false); RegisterAttribute("checked", HtmlTextWriterAttribute.Checked, false); RegisterAttribute("class", HtmlTextWriterAttribute.Class, true); RegisterAttribute("cols", HtmlTextWriterAttribute.Cols, false); RegisterAttribute("colspan", HtmlTextWriterAttribute.Colspan, false); RegisterAttribute("content", HtmlTextWriterAttribute.Content, true); RegisterAttribute("coords", HtmlTextWriterAttribute.Coords, false); RegisterAttribute("dir", HtmlTextWriterAttribute.Dir, false); RegisterAttribute("disabled", HtmlTextWriterAttribute.Disabled, false); RegisterAttribute("for", HtmlTextWriterAttribute.For, false); RegisterAttribute("headers", HtmlTextWriterAttribute.Headers, true); RegisterAttribute("height", HtmlTextWriterAttribute.Height, false); RegisterAttribute("href", HtmlTextWriterAttribute.Href, true, true); RegisterAttribute("id", HtmlTextWriterAttribute.Id, false); RegisterAttribute("longdesc", HtmlTextWriterAttribute.Longdesc, true, true); RegisterAttribute("maxlength", HtmlTextWriterAttribute.Maxlength, false); RegisterAttribute("multiple", HtmlTextWriterAttribute.Multiple, false); RegisterAttribute("name", HtmlTextWriterAttribute.Name, false); RegisterAttribute("nowrap", HtmlTextWriterAttribute.Nowrap, false); RegisterAttribute("onclick", HtmlTextWriterAttribute.Onclick, true); RegisterAttribute("onchange", HtmlTextWriterAttribute.Onchange, true); RegisterAttribute("readonly", HtmlTextWriterAttribute.ReadOnly, false); RegisterAttribute("rel", HtmlTextWriterAttribute.Rel, false); RegisterAttribute("rows", HtmlTextWriterAttribute.Rows, false); RegisterAttribute("rowspan", HtmlTextWriterAttribute.Rowspan, false); RegisterAttribute("rules", HtmlTextWriterAttribute.Rules, false); RegisterAttribute("scope", HtmlTextWriterAttribute.Scope, false); RegisterAttribute("selected", HtmlTextWriterAttribute.Selected, false); RegisterAttribute("shape", HtmlTextWriterAttribute.Shape, false); RegisterAttribute("size", HtmlTextWriterAttribute.Size, false); RegisterAttribute("src", HtmlTextWriterAttribute.Src, true, true); RegisterAttribute("style", HtmlTextWriterAttribute.Style, false); RegisterAttribute("tabindex", HtmlTextWriterAttribute.Tabindex, false); RegisterAttribute("target", HtmlTextWriterAttribute.Target, false); RegisterAttribute("title", HtmlTextWriterAttribute.Title, true); RegisterAttribute("type", HtmlTextWriterAttribute.Type, false); RegisterAttribute("usemap", HtmlTextWriterAttribute.Usemap, false); RegisterAttribute("valign", HtmlTextWriterAttribute.Valign, false); RegisterAttribute("value", HtmlTextWriterAttribute.Value, true); RegisterAttribute("vcard_name", HtmlTextWriterAttribute.VCardName, false); RegisterAttribute("width", HtmlTextWriterAttribute.Width, false); RegisterAttribute("wrap", HtmlTextWriterAttribute.Wrap, false); RegisterAttribute(DesignerRegionAttributeName, HtmlTextWriterAttribute.DesignerRegion, false); } public override Encoding Encoding { get { return writer.Encoding; } } // Gets or sets the new line character to use. public override string NewLine { get { return writer.NewLine; } set { writer.NewLine = value; } } // Gets or sets the number of spaces to indent. public int Indent { get { return indentLevel; } set { Debug.Assert(value >= 0, "Bogus Indent... probably caused by mismatched Indent++ and Indent--"); if (value < 0) { value = 0; } indentLevel = value; } } //Gets or sets the TextWriter to use. public TextWriter InnerWriter { get { return writer; } set { writer = value; _httpWriter = value as HttpWriter; } } /* // */ public virtual void BeginRender() { } //Closes the document being written to. public override void Close() { writer.Close(); } public virtual void EndRender() { } public virtual void EnterStyle(System.Web.UI.WebControls.Style style) { EnterStyle(style, HtmlTextWriterTag.Span); } public virtual void ExitStyle(System.Web.UI.WebControls.Style style) { ExitStyle(style, HtmlTextWriterTag.Span); } public override void Flush() { writer.Flush(); } protected virtual void OutputTabs() { if (tabsPending) { for (int i=0; i < indentLevel; i++) { writer.Write(tabString); } tabsPending = false; } } //Writes a string to the text stream. public override void Write(string s) { if (tabsPending) { OutputTabs(); } writer.Write(s); } //Writes the text representation of a Boolean value to the text stream. public override void Write(bool value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } //Writes a character to the text stream. public override void Write(char value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes a character array to the text stream. public override void Write(char[] buffer) { if (tabsPending) { OutputTabs(); } writer.Write(buffer); } // Writes a subarray of characters to the text stream. public override void Write(char[] buffer, int index, int count) { if (tabsPending) { OutputTabs(); } writer.Write(buffer, index, count); } // Writes the text representation of a Double to the text stream. public override void Write(double value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes the text representation of a Single to the text stream. public override void Write(float value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes the text representation of an integer to the text stream. public override void Write(int value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes the text representation of an 8-byte integer to the text stream. public override void Write(long value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes the text representation of an object to the text stream. public override void Write(object value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes out a formatted string, using the same semantics as specified. public override void Write(string format, object arg0) { if (tabsPending) { OutputTabs(); } writer.Write(format, arg0); } // Writes out a formatted string, using the same semantics as specified. public override void Write(string format, object arg0, object arg1) { if (tabsPending) { OutputTabs(); } writer.Write(format, arg0, arg1); } // Writes out a formatted string, using the same semantics as specified. public override void Write(string format, params object[] arg) { if (tabsPending) { OutputTabs(); } writer.Write(format, arg); } // Writes the specified string to a line without tabs. public void WriteLineNoTabs(string s) { writer.WriteLine(s); tabsPending = true; } // Writes the specified string followed by a line terminator to the text stream. public override void WriteLine(string s) { if (tabsPending) { OutputTabs(); } writer.WriteLine(s); tabsPending = true; } // Writes a line terminator. public override void WriteLine() { writer.WriteLine(); tabsPending = true; } // Writes the text representation of a Boolean followed by a line terminator to the text stream. public override void WriteLine(bool value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(char value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(char[] buffer) { if (tabsPending) { OutputTabs(); } writer.WriteLine(buffer); tabsPending = true; } public override void WriteLine(char[] buffer, int index, int count) { if (tabsPending) { OutputTabs(); } writer.WriteLine(buffer, index, count); tabsPending = true; } public override void WriteLine(double value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(float value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(int value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(long value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(object value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(string format, object arg0) { if (tabsPending) { OutputTabs(); } writer.WriteLine(format, arg0); tabsPending = true; } public override void WriteLine(string format, object arg0, object arg1) { if (tabsPending) { OutputTabs(); } writer.WriteLine(format, arg0, arg1); tabsPending = true; } public override void WriteLine(string format, params object[] arg) { if (tabsPending) { OutputTabs(); } writer.WriteLine(format, arg); tabsPending = true; } [CLSCompliant(false)] public override void WriteLine(UInt32 value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } protected static void RegisterTag(string name, HtmlTextWriterTag key) { RegisterTag(name, key, TagType.Other); } private static void RegisterTag(string name, HtmlTextWriterTag key, TagType type) { string nameLCase = name.ToLower(CultureInfo.InvariantCulture); _tagKeyLookupTable.Add(nameLCase, key); // Pre-resolve the end tag string endTag = null; if (type != TagType.NonClosing && key != HtmlTextWriterTag.Unknown) { endTag = EndTagLeftChars + nameLCase + TagRightChar.ToString(CultureInfo.InvariantCulture); } if ((int)key < _tagNameLookupArray.Length) { _tagNameLookupArray[(int)key] = new TagInformation(name, type, endTag); } } protected static void RegisterAttribute(string name, HtmlTextWriterAttribute key) { RegisterAttribute(name, key, false); } private static void RegisterAttribute(string name, HtmlTextWriterAttribute key, bool encode) { RegisterAttribute(name, key, encode, false); } private static void RegisterAttribute(string name, HtmlTextWriterAttribute key, bool encode, bool isUrl) { string nameLCase = name.ToLower(CultureInfo.InvariantCulture); _attrKeyLookupTable.Add(nameLCase, key); if ((int)key < _attrNameLookupArray.Length) { _attrNameLookupArray[(int)key] = new AttributeInformation(name, encode, isUrl); } } protected static void RegisterStyle(string name, HtmlTextWriterStyle key) { CssTextWriter.RegisterAttribute(name, key); } public HtmlTextWriter(TextWriter writer) : this(writer, DefaultTabString) { } public HtmlTextWriter(TextWriter writer, string tabString) : base(CultureInfo.InvariantCulture) { this.writer = writer; this.tabString = tabString; indentLevel = 0; tabsPending = false; // If it's an http writer, save it _httpWriter = writer as HttpWriter; _isDescendant = (GetType() != typeof(HtmlTextWriter)); _attrCount = 0; _styleCount = 0; _endTagCount = 0; _inlineCount = 0; } protected HtmlTextWriterTag TagKey { get { return _tagKey; } set { _tagIndex = (int) value; if (_tagIndex < 0 || _tagIndex >= _tagNameLookupArray.Length) { throw new ArgumentOutOfRangeException("value"); } _tagKey = value; // If explicitly setting to uknown, keep the old tag name. This allows a string tag // to be set without clobbering it if setting TagKey to itself. if (value != HtmlTextWriterTag.Unknown) { _tagName = _tagNameLookupArray[_tagIndex].name; } } } protected string TagName { get { return _tagName; } set { _tagName = value; _tagKey = GetTagKey(_tagName); _tagIndex = (int) _tagKey; Debug.Assert(_tagIndex >= 0 && _tagIndex < _tagNameLookupArray.Length); } } public virtual void AddAttribute(string name,string value) { HtmlTextWriterAttribute attributeKey = GetAttributeKey(name); value = EncodeAttributeValue(attributeKey, value); AddAttribute(name, value, attributeKey); } //do not fix this spelling error //believe it or not, it is a backwards breaking change for languages that //support late binding with named parameters VB.Net public virtual void AddAttribute(string name,string value, bool fEndode) { value = EncodeAttributeValue(value, fEndode); AddAttribute(name, value, GetAttributeKey(name)); } public virtual void AddAttribute(HtmlTextWriterAttribute key,string value) { int attributeIndex = (int) key; if (attributeIndex >= 0 && attributeIndex < _attrNameLookupArray.Length) { AttributeInformation info = _attrNameLookupArray[attributeIndex]; AddAttribute(info.name,value,key, info.encode, info.isUrl); } } public virtual void AddAttribute(HtmlTextWriterAttribute key,string value, bool fEncode) { int attributeIndex = (int) key; if (attributeIndex >= 0 && attributeIndex < _attrNameLookupArray.Length) { AttributeInformation info = _attrNameLookupArray[attributeIndex]; AddAttribute(info.name,value,key, fEncode, info.isUrl); } } protected virtual void AddAttribute(string name, string value, HtmlTextWriterAttribute key) { AddAttribute(name, value, key, false, false); } private void AddAttribute(string name, string value, HtmlTextWriterAttribute key, bool encode, bool isUrl) { if(_attrList == null) { _attrList = new RenderAttribute[20]; } else if (_attrCount >= _attrList.Length) { RenderAttribute[] newArray = new RenderAttribute[_attrList.Length * 2]; Array.Copy(_attrList, newArray, _attrList.Length); _attrList = newArray; } RenderAttribute attr; attr.name = name; attr.value = value; attr.key = key; attr.encode = encode; attr.isUrl = isUrl; _attrList[_attrCount] = attr; _attrCount++; } public virtual void AddStyleAttribute(string name, string value) { AddStyleAttribute(name, value, CssTextWriter.GetStyleKey(name)); } public virtual void AddStyleAttribute(HtmlTextWriterStyle key, string value) { AddStyleAttribute(CssTextWriter.GetStyleName(key), value, key); } protected virtual void AddStyleAttribute(string name, string value, HtmlTextWriterStyle key) { if(_styleList == null) { _styleList = new RenderStyle[20]; } else if (_styleCount > _styleList.Length) { RenderStyle[] newArray = new RenderStyle[_styleList.Length * 2]; Array.Copy(_styleList, newArray, _styleList.Length); _styleList = newArray; } RenderStyle style; style.name = name; style.key = key; string attributeValue = value; if (CssTextWriter.IsStyleEncoded(key)) { // note that only css attributes in an inline style value need to be attribute encoded // since CssTextWriter is used to render both embedded stylesheets and style attributes // the attribute encoding is done here. attributeValue = HttpUtility.HtmlAttributeEncode(value); } style.value = attributeValue; _styleList[_styleCount] = style; _styleCount++; } protected string EncodeAttributeValue(string value, bool fEncode) { if (value == null) { return null; } if (!fEncode) return value; return HttpUtility.HtmlAttributeEncode(value); } protected virtual string EncodeAttributeValue(HtmlTextWriterAttribute attrKey, string value) { bool encode = true; if (0 <= (int)attrKey && (int)attrKey < _attrNameLookupArray.Length) { encode = _attrNameLookupArray[(int)attrKey].encode; } return EncodeAttributeValue(value, encode); } // This does minimal URL encoding by converting spaces in the url to "%20". protected string EncodeUrl(string url) { // VSWhidbey 454348: escaped spaces in UNC share paths don't work in IE, so // we're not going to encode if it's a share. if (!UrlPath.IsUncSharePath(url)) { return HttpUtility.UrlPathEncode(url); } return url; } protected HtmlTextWriterAttribute GetAttributeKey(string attrName) { if (!String.IsNullOrEmpty(attrName)) { object key = _attrKeyLookupTable[attrName.ToLower(CultureInfo.InvariantCulture)]; if (key != null) return(HtmlTextWriterAttribute)key; } return(HtmlTextWriterAttribute)(-1); } protected string GetAttributeName(HtmlTextWriterAttribute attrKey) { if ((int)attrKey >= 0 && (int)attrKey < _attrNameLookupArray.Length) return _attrNameLookupArray[(int)attrKey].name; return string.Empty; } protected HtmlTextWriterStyle GetStyleKey(string styleName) { return CssTextWriter.GetStyleKey(styleName); } protected string GetStyleName(HtmlTextWriterStyle styleKey) { return CssTextWriter.GetStyleName(styleKey); } protected virtual HtmlTextWriterTag GetTagKey(string tagName) { if (!String.IsNullOrEmpty(tagName)) { object key = _tagKeyLookupTable[tagName.ToLower(CultureInfo.InvariantCulture)]; if (key != null) return(HtmlTextWriterTag)key; } return HtmlTextWriterTag.Unknown; } protected virtual string GetTagName(HtmlTextWriterTag tagKey) { int tagIndex = (int) tagKey; if (tagIndex >= 0 && tagIndex < _tagNameLookupArray.Length) return _tagNameLookupArray[tagIndex].name; return string.Empty; } protected bool IsAttributeDefined(HtmlTextWriterAttribute key) { for (int i = 0; i < _attrCount; i++) { if (_attrList[i].key == key) { return true; } } return false; } protected bool IsAttributeDefined(HtmlTextWriterAttribute key, out string value) { value = null; for (int i = 0; i < _attrCount; i++) { if (_attrList[i].key == key) { value = _attrList[i].value; return true; } } return false; } protected bool IsStyleAttributeDefined(HtmlTextWriterStyle key) { for (int i = 0; i < _styleCount; i++) { if (_styleList[i].key == key) { return true; } } return false; } protected bool IsStyleAttributeDefined(HtmlTextWriterStyle key, out string value) { value = null; for (int i = 0; i < _styleCount; i++) { if (_styleList[i].key == key) { value = _styleList[i].value; return true; } } return false; } protected virtual bool OnAttributeRender(string name, string value, HtmlTextWriterAttribute key) { return true; } protected virtual bool OnStyleAttributeRender(string name, string value, HtmlTextWriterStyle key) { return true; } protected virtual bool OnTagRender(string name, HtmlTextWriterTag key) { return true; } protected string PopEndTag() { if (_endTagCount <= 0) { throw new InvalidOperationException(SR.GetString(SR.HTMLTextWriterUnbalancedPop)); } _endTagCount--; TagKey = _endTags[_endTagCount].tagKey; return _endTags[_endTagCount].endTagText; } protected void PushEndTag(string endTag) { if(_endTags == null) { _endTags = new TagStackEntry[16]; } else if (_endTagCount >= _endTags.Length) { TagStackEntry[] newArray = new TagStackEntry[_endTags.Length * 2]; Array.Copy(_endTags, newArray, _endTags.Length); _endTags = newArray; } _endTags[_endTagCount].tagKey = _tagKey; _endTags[_endTagCount].endTagText= endTag; _endTagCount++; } // This calls filers out all attributes and style attributes by calling OnAttributeRender // and OnStyleAttributeRender on all properites and updates the lists protected virtual void FilterAttributes() { // Create the filtered list of styles int newStyleCount = 0; for (int i = 0; i < _styleCount; i++) { RenderStyle style = _styleList[i]; if (OnStyleAttributeRender(style.name, style.value, style.key)) { // Update the list. This can be done in place _styleList[newStyleCount] = style; newStyleCount++; } } // Update the count _styleCount = newStyleCount; // Create the filtered list of attributes int newAttrCount = 0; for (int i = 0; i < _attrCount; i++) { RenderAttribute attr = _attrList[i]; if (OnAttributeRender(attr.name, attr.value, attr.key)) { // Update the list. This can be done in place _attrList[newAttrCount] = attr; newAttrCount++; } } // Update the count _attrCount = newAttrCount; } public virtual void RenderBeginTag(string tagName) { this.TagName = tagName; RenderBeginTag(_tagKey); } public virtual void RenderBeginTag(HtmlTextWriterTag tagKey) { this.TagKey = tagKey; bool renderTag = true; if (_isDescendant) { renderTag = OnTagRender(_tagName, _tagKey); // Inherited renderers will be expecting to be able to filter any of the attributes at this point FilterAttributes(); // write text before begin tag string textBeforeTag = RenderBeforeTag(); if (textBeforeTag != null) { if (tabsPending) { OutputTabs(); } writer.Write(textBeforeTag); } } // gather information about this tag. TagInformation tagInfo = _tagNameLookupArray[_tagIndex]; TagType tagType = tagInfo.tagType; bool renderEndTag = renderTag && (tagType != TagType.NonClosing); string endTag = renderEndTag? tagInfo.closingTag : null; // write the begin tag if (renderTag) { if (tabsPending) { OutputTabs(); } writer.Write(TagLeftChar); writer.Write(_tagName); string styleValue = null; for (int i = 0; i < _attrCount; i++) { RenderAttribute attr = _attrList[i]; if (attr.key == HtmlTextWriterAttribute.Style) { // append style attribute in with other styles styleValue = attr.value; } else { writer.Write(SpaceChar); writer.Write(attr.name); if (attr.value != null) { writer.Write(EqualsDoubleQuoteString); string attrValue = attr.value; if (attr.isUrl) { if (attr.key != HtmlTextWriterAttribute.Href || !attrValue.StartsWith("javascript:", StringComparison.Ordinal)) { attrValue = EncodeUrl(attrValue); } } if (attr.encode) { WriteHtmlAttributeEncode(attrValue); } else { writer.Write(attrValue); } writer.Write(DoubleQuoteChar); } } } if (_styleCount > 0 || styleValue != null) { writer.Write(SpaceChar); writer.Write("style"); writer.Write(EqualsDoubleQuoteString); CssTextWriter.WriteAttributes(writer, _styleList, _styleCount); if (styleValue != null) { writer.Write(styleValue); } writer.Write(DoubleQuoteChar); } if (tagType == TagType.NonClosing) { writer.Write(SelfClosingTagEnd); } else { writer.Write(TagRightChar); } } string textBeforeContent = RenderBeforeContent(); if (textBeforeContent != null) { if (tabsPending) { OutputTabs(); } writer.Write(textBeforeContent); } // write text before the content if (renderEndTag) { if (tagType == TagType.Inline) { _inlineCount += 1; } else { // writeline and indent before rendering content WriteLine(); Indent++; } // Manually build end tags for unknown tag types. if (endTag == null) { endTag = EndTagLeftChars + _tagName + TagRightChar.ToString(CultureInfo.InvariantCulture); } } if (_isDescendant) { // append text after the tag string textAfterTag = RenderAfterTag(); if (textAfterTag != null) { endTag = (endTag == null) ? textAfterTag : textAfterTag + endTag; } // build end content and push it on stack to write in RenderEndTag // prepend text after the content string textAfterContent = RenderAfterContent(); if (textAfterContent != null) { endTag = (endTag == null) ? textAfterContent : textAfterContent + endTag; } } // push end tag onto stack PushEndTag(endTag); // flush attribute and style lists for next tag _attrCount = 0; _styleCount = 0; } public virtual void RenderEndTag() { string endTag = PopEndTag(); if (endTag != null) { if (_tagNameLookupArray[_tagIndex].tagType == TagType.Inline) { _inlineCount -= 1; // Never inject crlfs at end of inline tags. // Write(endTag); } else { // unindent if not an inline tag WriteLine(); this.Indent--; Write(endTag); } } } protected virtual string RenderBeforeTag() { return null; } protected virtual string RenderBeforeContent() { return null; } protected virtual string RenderAfterContent() { return null; } protected virtual string RenderAfterTag() { return null; } public virtual void WriteAttribute(string name, string value) { WriteAttribute(name, value, false /*encode*/); } public virtual void WriteAttribute(string name, string value, bool fEncode) { writer.Write(SpaceChar); writer.Write(name); if (value != null) { writer.Write(EqualsDoubleQuoteString); if (fEncode) { WriteHtmlAttributeEncode(value); } else { writer.Write(value); } writer.Write(DoubleQuoteChar); } } public virtual void WriteBeginTag(string tagName) { if (tabsPending) { OutputTabs(); } writer.Write(TagLeftChar); writer.Write(tagName); } public virtual void WriteBreak() { // Space between br and / is for improved html compatibility. See XHTML 1.0 specification, section C.2. Write("
"); } // DevDiv 33149: A backward compat. switch for Everett rendering internal void WriteObsoleteBreak() { Write("
"); } public virtual void WriteFullBeginTag(string tagName) { if (tabsPending) { OutputTabs(); } writer.Write(TagLeftChar); writer.Write(tagName); writer.Write(TagRightChar); } public virtual void WriteEndTag(string tagName) { if (tabsPending) { OutputTabs(); } writer.Write(TagLeftChar); writer.Write(SlashChar); writer.Write(tagName); writer.Write(TagRightChar); } public virtual void WriteStyleAttribute(string name, string value) { WriteStyleAttribute(name, value, false /*encode*/); } public virtual void WriteStyleAttribute(string name, string value, bool fEncode) { writer.Write(name); writer.Write(StyleEqualsChar); if (fEncode) { WriteHtmlAttributeEncode(value); } else { writer.Write(value); } writer.Write(SemicolonChar); } internal void WriteUTF8ResourceString(IntPtr pv, int offset, int size, bool fAsciiOnly) { // If we have an http writer, we can use the faster code path. Otherwise, // get a String out of the resource and write it. if (_httpWriter != null) { if (tabsPending) { OutputTabs(); } _httpWriter.WriteUTF8ResourceString(pv, offset, size, fAsciiOnly); } else { Write(StringResourceManager.ResourceToString(pv, offset, size)); } } public virtual void WriteEncodedUrl(String url) { int i = url.IndexOf('?'); if (i != -1) { WriteUrlEncodedString(url.Substring(0, i), false); Write(url.Substring(i)); } else { WriteUrlEncodedString(url, false); } } public virtual void WriteEncodedUrlParameter(String urlText) { WriteUrlEncodedString(urlText, true); } public virtual void WriteEncodedText(String text) { if (text == null) { throw new ArgumentNullException("text"); } const char NBSP = '\u00A0'; // When inner text is retrieved for a text control, is // decoded to 0x00A0 (code point for nbsp in Unicode). // HtmlEncode doesn't encode 0x00A0 to , we need to do it // manually here. int length = text.Length; int pos = 0; while (pos < length) { int nbsp = text.IndexOf(NBSP, pos); if (nbsp < 0) { HttpUtility.HtmlEncode(pos == 0 ? text : text.Substring(pos, length - pos), this); pos = length; } else { if (nbsp > pos) { HttpUtility.HtmlEncode(text.Substring(pos, nbsp - pos), this); } Write(" "); pos = nbsp + 1; } } } protected void WriteUrlEncodedString(String text, bool argument) { int length = text.Length; for (int i = 0; i < length; i++) { char ch = text[i]; if (HttpUtility.IsSafe(ch)) { Write(ch); } else if ( !argument && (ch == '/' || ch == ':' || ch == '#' || ch == ',' ) ) { Write(ch); } else if (ch == ' ' && argument) { Write('+'); } // for chars that their code number is less than 128 and have // not been handled above else if ((ch & 0xff80) == 0) { Write('%'); Write(HttpUtility.IntToHex((ch >> 4) & 0xf)); Write(HttpUtility.IntToHex((ch ) & 0xf)); } else { // VSWhidbey 448625: For DBCS characters, use UTF8 encoding // which can be handled by IIS5 and above. Write(HttpUtility.UrlEncodeNonAscii(Char.ToString(ch), Encoding.UTF8)); } } } internal void WriteHtmlAttributeEncode(string s) { if (_httpWriter == null) { HttpUtility.HtmlAttributeEncode(s, writer); } else { HttpUtility.HtmlAttributeEncodeInternal(s, _httpWriter); } } internal class Layout { private bool _wrap; private HorizontalAlign _align; /* public Layout(Layout currentLayout) { Align = currentLayout.Align; Wrap = currentLayout.Wrap; } */ public Layout(HorizontalAlign alignment, bool wrapping) { Align = alignment; Wrap = wrapping; } public bool Wrap { get { return _wrap; } set { _wrap = value; } } public HorizontalAlign Align { get { return _align; } set { _align = value; } } /* public bool Compare(Layout layout) { return Wrap == layout.Wrap && Align == layout.Align; } public void MergeWith(Layout layout) { if (Align == HorizontalAlign.NotSet) { Align = layout.Align; } if (Wrap) { Wrap = layout.Wrap; } } */ } private struct TagStackEntry { public HtmlTextWriterTag tagKey; public string endTagText; } private struct RenderAttribute { public string name; public string value; public HtmlTextWriterAttribute key; public bool encode; public bool isUrl; } private struct AttributeInformation { public string name; public bool isUrl; public bool encode; public AttributeInformation(string name, bool encode, bool isUrl) { this.name = name; this.encode = encode; this.isUrl = isUrl; } } private enum TagType { Inline, NonClosing, Other, } private struct TagInformation { public string name; public TagType tagType; public string closingTag; public TagInformation(string name, TagType tagType, string closingTag) { this.name = name; this.tagType = tagType; this.closingTag = closingTag; } } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. //------------------------------------------------------------------------------ //// Copyright (c) Microsoft Corporation. All rights reserved. // //----------------------------------------------------------------------------- // HtmlTextWriter.cs // namespace System.Web.UI { using System; using System.Collections; using System.Collections.Specialized; using System.IO; using System.Text; using System.Globalization; using System.Security.Permissions; using System.Web.UI.WebControls; using System.Web.Util; [AspNetHostingPermission(SecurityAction.LinkDemand, Level=AspNetHostingPermissionLevel.Minimal)] [AspNetHostingPermission(SecurityAction.InheritanceDemand, Level=AspNetHostingPermissionLevel.Minimal)] public class HtmlTextWriter : TextWriter { private Layout _currentLayout = new Layout(HorizontalAlign.NotSet, true /* wrap */); private Layout _currentWrittenLayout = null; internal virtual bool RenderDivAroundHiddenInputs { get { return true; } } #if SHIPPINGADAPTERS internal void CloseDiv(){ WriteEndTag("div"); } #endif public virtual void EnterStyle(Style style, HtmlTextWriterTag tag) { if (!style.IsEmpty || tag != HtmlTextWriterTag.Span) { style.AddAttributesToRender(this); RenderBeginTag(tag); } } public virtual void ExitStyle(System.Web.UI.WebControls.Style style, HtmlTextWriterTag tag) { // Review: This requires that the style doesn't change between beginstyle/endstyle. if (!style.IsEmpty || tag != HtmlTextWriterTag.Span) { RenderEndTag(); } } internal virtual void OpenDiv() { OpenDiv(_currentLayout, (_currentLayout != null) && (_currentLayout.Align != HorizontalAlign.NotSet), (_currentLayout != null) && !_currentLayout.Wrap); } private void OpenDiv(Layout layout, bool writeHorizontalAlign, bool writeWrapping) { WriteBeginTag("div"); if (writeHorizontalAlign) { String alignment; switch (layout.Align) { case HorizontalAlign.Right: alignment = "text-align:right"; break; case HorizontalAlign.Center: alignment = "text-align:center"; break; default: alignment = "text-align:left"; break; } WriteAttribute("style", alignment); } if (writeWrapping) { WriteAttribute("mode", layout.Wrap == true ? "wrap" : "nowrap"); } Write('>'); _currentWrittenLayout = layout; } public virtual bool IsValidFormAttribute(String attribute) { return true; } private TextWriter writer; private int indentLevel; private bool tabsPending; private string tabString; public const char TagLeftChar = '<'; public const char TagRightChar = '>'; public const string SelfClosingChars = " /"; public const string SelfClosingTagEnd = " />"; public const string EndTagLeftChars = ""; public const char DoubleQuoteChar = '"'; public const char SingleQuoteChar = '\''; public const char SpaceChar = ' '; public const char EqualsChar = '='; public const char SlashChar = '/'; public const string EqualsDoubleQuoteString = "=\""; public const char SemicolonChar = ';'; public const char StyleEqualsChar = ':'; public const string DefaultTabString = "\t"; // The DesignerRegion attribute name must be kept in [....] with // System.Web.UI.Design.DesignerRegion.DesignerRegionNameAttribute internal const string DesignerRegionAttributeName = "_designerRegion"; private static Hashtable _tagKeyLookupTable; private static Hashtable _attrKeyLookupTable; private static TagInformation[] _tagNameLookupArray; private static AttributeInformation[] _attrNameLookupArray; private RenderAttribute[] _attrList; private int _attrCount; private int _endTagCount; private TagStackEntry[] _endTags; private HttpWriter _httpWriter; private int _inlineCount; private bool _isDescendant; private RenderStyle[] _styleList; private int _styleCount; private int _tagIndex; private HtmlTextWriterTag _tagKey; private string _tagName; static HtmlTextWriter() { // register known tags _tagKeyLookupTable = new Hashtable((int)HtmlTextWriterTag.Xml + 1); _tagNameLookupArray = new TagInformation[(int)HtmlTextWriterTag.Xml + 1]; RegisterTag(String.Empty, HtmlTextWriterTag.Unknown, TagType.Other); RegisterTag("a", HtmlTextWriterTag.A, TagType.Inline); RegisterTag("acronym", HtmlTextWriterTag.Acronym, TagType.Inline); RegisterTag("address", HtmlTextWriterTag.Address, TagType.Other); RegisterTag("area", HtmlTextWriterTag.Area, TagType.NonClosing); RegisterTag("b", HtmlTextWriterTag.B, TagType.Inline); RegisterTag("base", HtmlTextWriterTag.Base, TagType.NonClosing); RegisterTag("basefont", HtmlTextWriterTag.Basefont, TagType.NonClosing); RegisterTag("bdo", HtmlTextWriterTag.Bdo, TagType.Inline); RegisterTag("bgsound", HtmlTextWriterTag.Bgsound, TagType.NonClosing); RegisterTag("big", HtmlTextWriterTag.Big, TagType.Inline); RegisterTag("blockquote", HtmlTextWriterTag.Blockquote, TagType.Other); RegisterTag("body", HtmlTextWriterTag.Body, TagType.Other); RegisterTag("br", HtmlTextWriterTag.Br, TagType.Other); RegisterTag("button", HtmlTextWriterTag.Button, TagType.Inline); RegisterTag("caption", HtmlTextWriterTag.Caption, TagType.Other); RegisterTag("center", HtmlTextWriterTag.Center, TagType.Other); RegisterTag("cite", HtmlTextWriterTag.Cite, TagType.Inline); RegisterTag("code", HtmlTextWriterTag.Code, TagType.Inline); RegisterTag("col", HtmlTextWriterTag.Col, TagType.NonClosing); RegisterTag("colgroup", HtmlTextWriterTag.Colgroup, TagType.Other); RegisterTag("del", HtmlTextWriterTag.Del, TagType.Inline); RegisterTag("dd", HtmlTextWriterTag.Dd, TagType.Inline); RegisterTag("dfn", HtmlTextWriterTag.Dfn, TagType.Inline); RegisterTag("dir", HtmlTextWriterTag.Dir, TagType.Other); RegisterTag("div", HtmlTextWriterTag.Div, TagType.Other); RegisterTag("dl", HtmlTextWriterTag.Dl, TagType.Other); RegisterTag("dt", HtmlTextWriterTag.Dt, TagType.Inline); RegisterTag("em", HtmlTextWriterTag.Em, TagType.Inline); RegisterTag("embed", HtmlTextWriterTag.Embed, TagType.NonClosing); RegisterTag("fieldset", HtmlTextWriterTag.Fieldset, TagType.Other); RegisterTag("font", HtmlTextWriterTag.Font, TagType.Inline); RegisterTag("form", HtmlTextWriterTag.Form, TagType.Other); RegisterTag("frame", HtmlTextWriterTag.Frame, TagType.NonClosing); RegisterTag("frameset", HtmlTextWriterTag.Frameset, TagType.Other); RegisterTag("h1", HtmlTextWriterTag.H1, TagType.Other); RegisterTag("h2", HtmlTextWriterTag.H2, TagType.Other); RegisterTag("h3", HtmlTextWriterTag.H3, TagType.Other); RegisterTag("h4", HtmlTextWriterTag.H4, TagType.Other); RegisterTag("h5", HtmlTextWriterTag.H5, TagType.Other); RegisterTag("h6", HtmlTextWriterTag.H6, TagType.Other); RegisterTag("head", HtmlTextWriterTag.Head, TagType.Other); RegisterTag("hr", HtmlTextWriterTag.Hr, TagType.NonClosing); RegisterTag("html", HtmlTextWriterTag.Html, TagType.Other); RegisterTag("i", HtmlTextWriterTag.I, TagType.Inline); RegisterTag("iframe", HtmlTextWriterTag.Iframe, TagType.Other); RegisterTag("img", HtmlTextWriterTag.Img, TagType.NonClosing); RegisterTag("input", HtmlTextWriterTag.Input, TagType.NonClosing); RegisterTag("ins", HtmlTextWriterTag.Ins, TagType.Inline); RegisterTag("isindex", HtmlTextWriterTag.Isindex, TagType.NonClosing); RegisterTag("kbd", HtmlTextWriterTag.Kbd, TagType.Inline); RegisterTag("label", HtmlTextWriterTag.Label, TagType.Inline); RegisterTag("legend", HtmlTextWriterTag.Legend, TagType.Other); RegisterTag("li", HtmlTextWriterTag.Li, TagType.Inline); RegisterTag("link", HtmlTextWriterTag.Link, TagType.NonClosing); RegisterTag("map", HtmlTextWriterTag.Map, TagType.Other); RegisterTag("marquee", HtmlTextWriterTag.Marquee, TagType.Other); RegisterTag("menu", HtmlTextWriterTag.Menu, TagType.Other); RegisterTag("meta", HtmlTextWriterTag.Meta, TagType.NonClosing); RegisterTag("nobr", HtmlTextWriterTag.Nobr, TagType.Inline); RegisterTag("noframes", HtmlTextWriterTag.Noframes, TagType.Other); RegisterTag("noscript", HtmlTextWriterTag.Noscript, TagType.Other); RegisterTag("object", HtmlTextWriterTag.Object, TagType.Other); RegisterTag("ol", HtmlTextWriterTag.Ol, TagType.Other); RegisterTag("option", HtmlTextWriterTag.Option, TagType.Other); RegisterTag("p", HtmlTextWriterTag.P, TagType.Inline); RegisterTag("param", HtmlTextWriterTag.Param, TagType.Other); RegisterTag("pre", HtmlTextWriterTag.Pre, TagType.Other); RegisterTag("ruby", HtmlTextWriterTag.Ruby, TagType.Other); RegisterTag("rt", HtmlTextWriterTag.Rt, TagType.Other); RegisterTag("q", HtmlTextWriterTag.Q, TagType.Inline); RegisterTag("s", HtmlTextWriterTag.S, TagType.Inline); RegisterTag("samp", HtmlTextWriterTag.Samp, TagType.Inline); RegisterTag("script", HtmlTextWriterTag.Script, TagType.Other); RegisterTag("select", HtmlTextWriterTag.Select, TagType.Other); RegisterTag("small", HtmlTextWriterTag.Small, TagType.Other); RegisterTag("span", HtmlTextWriterTag.Span, TagType.Inline); RegisterTag("strike", HtmlTextWriterTag.Strike, TagType.Inline); RegisterTag("strong", HtmlTextWriterTag.Strong, TagType.Inline); RegisterTag("style", HtmlTextWriterTag.Style, TagType.Other); RegisterTag("sub", HtmlTextWriterTag.Sub, TagType.Inline); RegisterTag("sup", HtmlTextWriterTag.Sup, TagType.Inline); RegisterTag("table", HtmlTextWriterTag.Table, TagType.Other); RegisterTag("tbody", HtmlTextWriterTag.Tbody, TagType.Other); RegisterTag("td", HtmlTextWriterTag.Td, TagType.Inline); RegisterTag("textarea", HtmlTextWriterTag.Textarea, TagType.Inline); RegisterTag("tfoot", HtmlTextWriterTag.Tfoot, TagType.Other); RegisterTag("th", HtmlTextWriterTag.Th, TagType.Inline); RegisterTag("thead", HtmlTextWriterTag.Thead, TagType.Other); RegisterTag("title", HtmlTextWriterTag.Title, TagType.Other); RegisterTag("tr", HtmlTextWriterTag.Tr, TagType.Other); RegisterTag("tt", HtmlTextWriterTag.Tt, TagType.Inline); RegisterTag("u", HtmlTextWriterTag.U, TagType.Inline); RegisterTag("ul", HtmlTextWriterTag.Ul, TagType.Other); RegisterTag("var", HtmlTextWriterTag.Var, TagType.Inline); RegisterTag("wbr", HtmlTextWriterTag.Wbr, TagType.NonClosing); RegisterTag("xml", HtmlTextWriterTag.Xml, TagType.Other); // register known attributes _attrKeyLookupTable = new Hashtable((int)HtmlTextWriterAttribute.VCardName + 1); _attrNameLookupArray = new AttributeInformation[(int)HtmlTextWriterAttribute.VCardName + 1]; RegisterAttribute("abbr", HtmlTextWriterAttribute.Abbr, true); RegisterAttribute("accesskey", HtmlTextWriterAttribute.Accesskey, true); RegisterAttribute("align", HtmlTextWriterAttribute.Align, false); RegisterAttribute("alt", HtmlTextWriterAttribute.Alt, true); RegisterAttribute("autocomplete", HtmlTextWriterAttribute.AutoComplete, false); RegisterAttribute("axis", HtmlTextWriterAttribute.Axis, true); RegisterAttribute("background", HtmlTextWriterAttribute.Background, true, true); RegisterAttribute("bgcolor", HtmlTextWriterAttribute.Bgcolor, false); RegisterAttribute("border", HtmlTextWriterAttribute.Border, false); RegisterAttribute("bordercolor", HtmlTextWriterAttribute.Bordercolor, false); RegisterAttribute("cellpadding", HtmlTextWriterAttribute.Cellpadding, false); RegisterAttribute("cellspacing", HtmlTextWriterAttribute.Cellspacing, false); RegisterAttribute("checked", HtmlTextWriterAttribute.Checked, false); RegisterAttribute("class", HtmlTextWriterAttribute.Class, true); RegisterAttribute("cols", HtmlTextWriterAttribute.Cols, false); RegisterAttribute("colspan", HtmlTextWriterAttribute.Colspan, false); RegisterAttribute("content", HtmlTextWriterAttribute.Content, true); RegisterAttribute("coords", HtmlTextWriterAttribute.Coords, false); RegisterAttribute("dir", HtmlTextWriterAttribute.Dir, false); RegisterAttribute("disabled", HtmlTextWriterAttribute.Disabled, false); RegisterAttribute("for", HtmlTextWriterAttribute.For, false); RegisterAttribute("headers", HtmlTextWriterAttribute.Headers, true); RegisterAttribute("height", HtmlTextWriterAttribute.Height, false); RegisterAttribute("href", HtmlTextWriterAttribute.Href, true, true); RegisterAttribute("id", HtmlTextWriterAttribute.Id, false); RegisterAttribute("longdesc", HtmlTextWriterAttribute.Longdesc, true, true); RegisterAttribute("maxlength", HtmlTextWriterAttribute.Maxlength, false); RegisterAttribute("multiple", HtmlTextWriterAttribute.Multiple, false); RegisterAttribute("name", HtmlTextWriterAttribute.Name, false); RegisterAttribute("nowrap", HtmlTextWriterAttribute.Nowrap, false); RegisterAttribute("onclick", HtmlTextWriterAttribute.Onclick, true); RegisterAttribute("onchange", HtmlTextWriterAttribute.Onchange, true); RegisterAttribute("readonly", HtmlTextWriterAttribute.ReadOnly, false); RegisterAttribute("rel", HtmlTextWriterAttribute.Rel, false); RegisterAttribute("rows", HtmlTextWriterAttribute.Rows, false); RegisterAttribute("rowspan", HtmlTextWriterAttribute.Rowspan, false); RegisterAttribute("rules", HtmlTextWriterAttribute.Rules, false); RegisterAttribute("scope", HtmlTextWriterAttribute.Scope, false); RegisterAttribute("selected", HtmlTextWriterAttribute.Selected, false); RegisterAttribute("shape", HtmlTextWriterAttribute.Shape, false); RegisterAttribute("size", HtmlTextWriterAttribute.Size, false); RegisterAttribute("src", HtmlTextWriterAttribute.Src, true, true); RegisterAttribute("style", HtmlTextWriterAttribute.Style, false); RegisterAttribute("tabindex", HtmlTextWriterAttribute.Tabindex, false); RegisterAttribute("target", HtmlTextWriterAttribute.Target, false); RegisterAttribute("title", HtmlTextWriterAttribute.Title, true); RegisterAttribute("type", HtmlTextWriterAttribute.Type, false); RegisterAttribute("usemap", HtmlTextWriterAttribute.Usemap, false); RegisterAttribute("valign", HtmlTextWriterAttribute.Valign, false); RegisterAttribute("value", HtmlTextWriterAttribute.Value, true); RegisterAttribute("vcard_name", HtmlTextWriterAttribute.VCardName, false); RegisterAttribute("width", HtmlTextWriterAttribute.Width, false); RegisterAttribute("wrap", HtmlTextWriterAttribute.Wrap, false); RegisterAttribute(DesignerRegionAttributeName, HtmlTextWriterAttribute.DesignerRegion, false); } public override Encoding Encoding { get { return writer.Encoding; } } // Gets or sets the new line character to use. public override string NewLine { get { return writer.NewLine; } set { writer.NewLine = value; } } // Gets or sets the number of spaces to indent. public int Indent { get { return indentLevel; } set { Debug.Assert(value >= 0, "Bogus Indent... probably caused by mismatched Indent++ and Indent--"); if (value < 0) { value = 0; } indentLevel = value; } } //Gets or sets the TextWriter to use. public TextWriter InnerWriter { get { return writer; } set { writer = value; _httpWriter = value as HttpWriter; } } /* // */ public virtual void BeginRender() { } //Closes the document being written to. public override void Close() { writer.Close(); } public virtual void EndRender() { } public virtual void EnterStyle(System.Web.UI.WebControls.Style style) { EnterStyle(style, HtmlTextWriterTag.Span); } public virtual void ExitStyle(System.Web.UI.WebControls.Style style) { ExitStyle(style, HtmlTextWriterTag.Span); } public override void Flush() { writer.Flush(); } protected virtual void OutputTabs() { if (tabsPending) { for (int i=0; i < indentLevel; i++) { writer.Write(tabString); } tabsPending = false; } } //Writes a string to the text stream. public override void Write(string s) { if (tabsPending) { OutputTabs(); } writer.Write(s); } //Writes the text representation of a Boolean value to the text stream. public override void Write(bool value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } //Writes a character to the text stream. public override void Write(char value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes a character array to the text stream. public override void Write(char[] buffer) { if (tabsPending) { OutputTabs(); } writer.Write(buffer); } // Writes a subarray of characters to the text stream. public override void Write(char[] buffer, int index, int count) { if (tabsPending) { OutputTabs(); } writer.Write(buffer, index, count); } // Writes the text representation of a Double to the text stream. public override void Write(double value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes the text representation of a Single to the text stream. public override void Write(float value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes the text representation of an integer to the text stream. public override void Write(int value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes the text representation of an 8-byte integer to the text stream. public override void Write(long value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes the text representation of an object to the text stream. public override void Write(object value) { if (tabsPending) { OutputTabs(); } writer.Write(value); } // Writes out a formatted string, using the same semantics as specified. public override void Write(string format, object arg0) { if (tabsPending) { OutputTabs(); } writer.Write(format, arg0); } // Writes out a formatted string, using the same semantics as specified. public override void Write(string format, object arg0, object arg1) { if (tabsPending) { OutputTabs(); } writer.Write(format, arg0, arg1); } // Writes out a formatted string, using the same semantics as specified. public override void Write(string format, params object[] arg) { if (tabsPending) { OutputTabs(); } writer.Write(format, arg); } // Writes the specified string to a line without tabs. public void WriteLineNoTabs(string s) { writer.WriteLine(s); tabsPending = true; } // Writes the specified string followed by a line terminator to the text stream. public override void WriteLine(string s) { if (tabsPending) { OutputTabs(); } writer.WriteLine(s); tabsPending = true; } // Writes a line terminator. public override void WriteLine() { writer.WriteLine(); tabsPending = true; } // Writes the text representation of a Boolean followed by a line terminator to the text stream. public override void WriteLine(bool value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(char value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(char[] buffer) { if (tabsPending) { OutputTabs(); } writer.WriteLine(buffer); tabsPending = true; } public override void WriteLine(char[] buffer, int index, int count) { if (tabsPending) { OutputTabs(); } writer.WriteLine(buffer, index, count); tabsPending = true; } public override void WriteLine(double value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(float value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(int value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(long value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(object value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } public override void WriteLine(string format, object arg0) { if (tabsPending) { OutputTabs(); } writer.WriteLine(format, arg0); tabsPending = true; } public override void WriteLine(string format, object arg0, object arg1) { if (tabsPending) { OutputTabs(); } writer.WriteLine(format, arg0, arg1); tabsPending = true; } public override void WriteLine(string format, params object[] arg) { if (tabsPending) { OutputTabs(); } writer.WriteLine(format, arg); tabsPending = true; } [CLSCompliant(false)] public override void WriteLine(UInt32 value) { if (tabsPending) { OutputTabs(); } writer.WriteLine(value); tabsPending = true; } protected static void RegisterTag(string name, HtmlTextWriterTag key) { RegisterTag(name, key, TagType.Other); } private static void RegisterTag(string name, HtmlTextWriterTag key, TagType type) { string nameLCase = name.ToLower(CultureInfo.InvariantCulture); _tagKeyLookupTable.Add(nameLCase, key); // Pre-resolve the end tag string endTag = null; if (type != TagType.NonClosing && key != HtmlTextWriterTag.Unknown) { endTag = EndTagLeftChars + nameLCase + TagRightChar.ToString(CultureInfo.InvariantCulture); } if ((int)key < _tagNameLookupArray.Length) { _tagNameLookupArray[(int)key] = new TagInformation(name, type, endTag); } } protected static void RegisterAttribute(string name, HtmlTextWriterAttribute key) { RegisterAttribute(name, key, false); } private static void RegisterAttribute(string name, HtmlTextWriterAttribute key, bool encode) { RegisterAttribute(name, key, encode, false); } private static void RegisterAttribute(string name, HtmlTextWriterAttribute key, bool encode, bool isUrl) { string nameLCase = name.ToLower(CultureInfo.InvariantCulture); _attrKeyLookupTable.Add(nameLCase, key); if ((int)key < _attrNameLookupArray.Length) { _attrNameLookupArray[(int)key] = new AttributeInformation(name, encode, isUrl); } } protected static void RegisterStyle(string name, HtmlTextWriterStyle key) { CssTextWriter.RegisterAttribute(name, key); } public HtmlTextWriter(TextWriter writer) : this(writer, DefaultTabString) { } public HtmlTextWriter(TextWriter writer, string tabString) : base(CultureInfo.InvariantCulture) { this.writer = writer; this.tabString = tabString; indentLevel = 0; tabsPending = false; // If it's an http writer, save it _httpWriter = writer as HttpWriter; _isDescendant = (GetType() != typeof(HtmlTextWriter)); _attrCount = 0; _styleCount = 0; _endTagCount = 0; _inlineCount = 0; } protected HtmlTextWriterTag TagKey { get { return _tagKey; } set { _tagIndex = (int) value; if (_tagIndex < 0 || _tagIndex >= _tagNameLookupArray.Length) { throw new ArgumentOutOfRangeException("value"); } _tagKey = value; // If explicitly setting to uknown, keep the old tag name. This allows a string tag // to be set without clobbering it if setting TagKey to itself. if (value != HtmlTextWriterTag.Unknown) { _tagName = _tagNameLookupArray[_tagIndex].name; } } } protected string TagName { get { return _tagName; } set { _tagName = value; _tagKey = GetTagKey(_tagName); _tagIndex = (int) _tagKey; Debug.Assert(_tagIndex >= 0 && _tagIndex < _tagNameLookupArray.Length); } } public virtual void AddAttribute(string name,string value) { HtmlTextWriterAttribute attributeKey = GetAttributeKey(name); value = EncodeAttributeValue(attributeKey, value); AddAttribute(name, value, attributeKey); } //do not fix this spelling error //believe it or not, it is a backwards breaking change for languages that //support late binding with named parameters VB.Net public virtual void AddAttribute(string name,string value, bool fEndode) { value = EncodeAttributeValue(value, fEndode); AddAttribute(name, value, GetAttributeKey(name)); } public virtual void AddAttribute(HtmlTextWriterAttribute key,string value) { int attributeIndex = (int) key; if (attributeIndex >= 0 && attributeIndex < _attrNameLookupArray.Length) { AttributeInformation info = _attrNameLookupArray[attributeIndex]; AddAttribute(info.name,value,key, info.encode, info.isUrl); } } public virtual void AddAttribute(HtmlTextWriterAttribute key,string value, bool fEncode) { int attributeIndex = (int) key; if (attributeIndex >= 0 && attributeIndex < _attrNameLookupArray.Length) { AttributeInformation info = _attrNameLookupArray[attributeIndex]; AddAttribute(info.name,value,key, fEncode, info.isUrl); } } protected virtual void AddAttribute(string name, string value, HtmlTextWriterAttribute key) { AddAttribute(name, value, key, false, false); } private void AddAttribute(string name, string value, HtmlTextWriterAttribute key, bool encode, bool isUrl) { if(_attrList == null) { _attrList = new RenderAttribute[20]; } else if (_attrCount >= _attrList.Length) { RenderAttribute[] newArray = new RenderAttribute[_attrList.Length * 2]; Array.Copy(_attrList, newArray, _attrList.Length); _attrList = newArray; } RenderAttribute attr; attr.name = name; attr.value = value; attr.key = key; attr.encode = encode; attr.isUrl = isUrl; _attrList[_attrCount] = attr; _attrCount++; } public virtual void AddStyleAttribute(string name, string value) { AddStyleAttribute(name, value, CssTextWriter.GetStyleKey(name)); } public virtual void AddStyleAttribute(HtmlTextWriterStyle key, string value) { AddStyleAttribute(CssTextWriter.GetStyleName(key), value, key); } protected virtual void AddStyleAttribute(string name, string value, HtmlTextWriterStyle key) { if(_styleList == null) { _styleList = new RenderStyle[20]; } else if (_styleCount > _styleList.Length) { RenderStyle[] newArray = new RenderStyle[_styleList.Length * 2]; Array.Copy(_styleList, newArray, _styleList.Length); _styleList = newArray; } RenderStyle style; style.name = name; style.key = key; string attributeValue = value; if (CssTextWriter.IsStyleEncoded(key)) { // note that only css attributes in an inline style value need to be attribute encoded // since CssTextWriter is used to render both embedded stylesheets and style attributes // the attribute encoding is done here. attributeValue = HttpUtility.HtmlAttributeEncode(value); } style.value = attributeValue; _styleList[_styleCount] = style; _styleCount++; } protected string EncodeAttributeValue(string value, bool fEncode) { if (value == null) { return null; } if (!fEncode) return value; return HttpUtility.HtmlAttributeEncode(value); } protected virtual string EncodeAttributeValue(HtmlTextWriterAttribute attrKey, string value) { bool encode = true; if (0 <= (int)attrKey && (int)attrKey < _attrNameLookupArray.Length) { encode = _attrNameLookupArray[(int)attrKey].encode; } return EncodeAttributeValue(value, encode); } // This does minimal URL encoding by converting spaces in the url to "%20". protected string EncodeUrl(string url) { // VSWhidbey 454348: escaped spaces in UNC share paths don't work in IE, so // we're not going to encode if it's a share. if (!UrlPath.IsUncSharePath(url)) { return HttpUtility.UrlPathEncode(url); } return url; } protected HtmlTextWriterAttribute GetAttributeKey(string attrName) { if (!String.IsNullOrEmpty(attrName)) { object key = _attrKeyLookupTable[attrName.ToLower(CultureInfo.InvariantCulture)]; if (key != null) return(HtmlTextWriterAttribute)key; } return(HtmlTextWriterAttribute)(-1); } protected string GetAttributeName(HtmlTextWriterAttribute attrKey) { if ((int)attrKey >= 0 && (int)attrKey < _attrNameLookupArray.Length) return _attrNameLookupArray[(int)attrKey].name; return string.Empty; } protected HtmlTextWriterStyle GetStyleKey(string styleName) { return CssTextWriter.GetStyleKey(styleName); } protected string GetStyleName(HtmlTextWriterStyle styleKey) { return CssTextWriter.GetStyleName(styleKey); } protected virtual HtmlTextWriterTag GetTagKey(string tagName) { if (!String.IsNullOrEmpty(tagName)) { object key = _tagKeyLookupTable[tagName.ToLower(CultureInfo.InvariantCulture)]; if (key != null) return(HtmlTextWriterTag)key; } return HtmlTextWriterTag.Unknown; } protected virtual string GetTagName(HtmlTextWriterTag tagKey) { int tagIndex = (int) tagKey; if (tagIndex >= 0 && tagIndex < _tagNameLookupArray.Length) return _tagNameLookupArray[tagIndex].name; return string.Empty; } protected bool IsAttributeDefined(HtmlTextWriterAttribute key) { for (int i = 0; i < _attrCount; i++) { if (_attrList[i].key == key) { return true; } } return false; } protected bool IsAttributeDefined(HtmlTextWriterAttribute key, out string value) { value = null; for (int i = 0; i < _attrCount; i++) { if (_attrList[i].key == key) { value = _attrList[i].value; return true; } } return false; } protected bool IsStyleAttributeDefined(HtmlTextWriterStyle key) { for (int i = 0; i < _styleCount; i++) { if (_styleList[i].key == key) { return true; } } return false; } protected bool IsStyleAttributeDefined(HtmlTextWriterStyle key, out string value) { value = null; for (int i = 0; i < _styleCount; i++) { if (_styleList[i].key == key) { value = _styleList[i].value; return true; } } return false; } protected virtual bool OnAttributeRender(string name, string value, HtmlTextWriterAttribute key) { return true; } protected virtual bool OnStyleAttributeRender(string name, string value, HtmlTextWriterStyle key) { return true; } protected virtual bool OnTagRender(string name, HtmlTextWriterTag key) { return true; } protected string PopEndTag() { if (_endTagCount <= 0) { throw new InvalidOperationException(SR.GetString(SR.HTMLTextWriterUnbalancedPop)); } _endTagCount--; TagKey = _endTags[_endTagCount].tagKey; return _endTags[_endTagCount].endTagText; } protected void PushEndTag(string endTag) { if(_endTags == null) { _endTags = new TagStackEntry[16]; } else if (_endTagCount >= _endTags.Length) { TagStackEntry[] newArray = new TagStackEntry[_endTags.Length * 2]; Array.Copy(_endTags, newArray, _endTags.Length); _endTags = newArray; } _endTags[_endTagCount].tagKey = _tagKey; _endTags[_endTagCount].endTagText= endTag; _endTagCount++; } // This calls filers out all attributes and style attributes by calling OnAttributeRender // and OnStyleAttributeRender on all properites and updates the lists protected virtual void FilterAttributes() { // Create the filtered list of styles int newStyleCount = 0; for (int i = 0; i < _styleCount; i++) { RenderStyle style = _styleList[i]; if (OnStyleAttributeRender(style.name, style.value, style.key)) { // Update the list. This can be done in place _styleList[newStyleCount] = style; newStyleCount++; } } // Update the count _styleCount = newStyleCount; // Create the filtered list of attributes int newAttrCount = 0; for (int i = 0; i < _attrCount; i++) { RenderAttribute attr = _attrList[i]; if (OnAttributeRender(attr.name, attr.value, attr.key)) { // Update the list. This can be done in place _attrList[newAttrCount] = attr; newAttrCount++; } } // Update the count _attrCount = newAttrCount; } public virtual void RenderBeginTag(string tagName) { this.TagName = tagName; RenderBeginTag(_tagKey); } public virtual void RenderBeginTag(HtmlTextWriterTag tagKey) { this.TagKey = tagKey; bool renderTag = true; if (_isDescendant) { renderTag = OnTagRender(_tagName, _tagKey); // Inherited renderers will be expecting to be able to filter any of the attributes at this point FilterAttributes(); // write text before begin tag string textBeforeTag = RenderBeforeTag(); if (textBeforeTag != null) { if (tabsPending) { OutputTabs(); } writer.Write(textBeforeTag); } } // gather information about this tag. TagInformation tagInfo = _tagNameLookupArray[_tagIndex]; TagType tagType = tagInfo.tagType; bool renderEndTag = renderTag && (tagType != TagType.NonClosing); string endTag = renderEndTag? tagInfo.closingTag : null; // write the begin tag if (renderTag) { if (tabsPending) { OutputTabs(); } writer.Write(TagLeftChar); writer.Write(_tagName); string styleValue = null; for (int i = 0; i < _attrCount; i++) { RenderAttribute attr = _attrList[i]; if (attr.key == HtmlTextWriterAttribute.Style) { // append style attribute in with other styles styleValue = attr.value; } else { writer.Write(SpaceChar); writer.Write(attr.name); if (attr.value != null) { writer.Write(EqualsDoubleQuoteString); string attrValue = attr.value; if (attr.isUrl) { if (attr.key != HtmlTextWriterAttribute.Href || !attrValue.StartsWith("javascript:", StringComparison.Ordinal)) { attrValue = EncodeUrl(attrValue); } } if (attr.encode) { WriteHtmlAttributeEncode(attrValue); } else { writer.Write(attrValue); } writer.Write(DoubleQuoteChar); } } } if (_styleCount > 0 || styleValue != null) { writer.Write(SpaceChar); writer.Write("style"); writer.Write(EqualsDoubleQuoteString); CssTextWriter.WriteAttributes(writer, _styleList, _styleCount); if (styleValue != null) { writer.Write(styleValue); } writer.Write(DoubleQuoteChar); } if (tagType == TagType.NonClosing) { writer.Write(SelfClosingTagEnd); } else { writer.Write(TagRightChar); } } string textBeforeContent = RenderBeforeContent(); if (textBeforeContent != null) { if (tabsPending) { OutputTabs(); } writer.Write(textBeforeContent); } // write text before the content if (renderEndTag) { if (tagType == TagType.Inline) { _inlineCount += 1; } else { // writeline and indent before rendering content WriteLine(); Indent++; } // Manually build end tags for unknown tag types. if (endTag == null) { endTag = EndTagLeftChars + _tagName + TagRightChar.ToString(CultureInfo.InvariantCulture); } } if (_isDescendant) { // append text after the tag string textAfterTag = RenderAfterTag(); if (textAfterTag != null) { endTag = (endTag == null) ? textAfterTag : textAfterTag + endTag; } // build end content and push it on stack to write in RenderEndTag // prepend text after the content string textAfterContent = RenderAfterContent(); if (textAfterContent != null) { endTag = (endTag == null) ? textAfterContent : textAfterContent + endTag; } } // push end tag onto stack PushEndTag(endTag); // flush attribute and style lists for next tag _attrCount = 0; _styleCount = 0; } public virtual void RenderEndTag() { string endTag = PopEndTag(); if (endTag != null) { if (_tagNameLookupArray[_tagIndex].tagType == TagType.Inline) { _inlineCount -= 1; // Never inject crlfs at end of inline tags. // Write(endTag); } else { // unindent if not an inline tag WriteLine(); this.Indent--; Write(endTag); } } } protected virtual string RenderBeforeTag() { return null; } protected virtual string RenderBeforeContent() { return null; } protected virtual string RenderAfterContent() { return null; } protected virtual string RenderAfterTag() { return null; } public virtual void WriteAttribute(string name, string value) { WriteAttribute(name, value, false /*encode*/); } public virtual void WriteAttribute(string name, string value, bool fEncode) { writer.Write(SpaceChar); writer.Write(name); if (value != null) { writer.Write(EqualsDoubleQuoteString); if (fEncode) { WriteHtmlAttributeEncode(value); } else { writer.Write(value); } writer.Write(DoubleQuoteChar); } } public virtual void WriteBeginTag(string tagName) { if (tabsPending) { OutputTabs(); } writer.Write(TagLeftChar); writer.Write(tagName); } public virtual void WriteBreak() { // Space between br and / is for improved html compatibility. See XHTML 1.0 specification, section C.2. Write("
"); } // DevDiv 33149: A backward compat. switch for Everett rendering internal void WriteObsoleteBreak() { Write("
"); } public virtual void WriteFullBeginTag(string tagName) { if (tabsPending) { OutputTabs(); } writer.Write(TagLeftChar); writer.Write(tagName); writer.Write(TagRightChar); } public virtual void WriteEndTag(string tagName) { if (tabsPending) { OutputTabs(); } writer.Write(TagLeftChar); writer.Write(SlashChar); writer.Write(tagName); writer.Write(TagRightChar); } public virtual void WriteStyleAttribute(string name, string value) { WriteStyleAttribute(name, value, false /*encode*/); } public virtual void WriteStyleAttribute(string name, string value, bool fEncode) { writer.Write(name); writer.Write(StyleEqualsChar); if (fEncode) { WriteHtmlAttributeEncode(value); } else { writer.Write(value); } writer.Write(SemicolonChar); } internal void WriteUTF8ResourceString(IntPtr pv, int offset, int size, bool fAsciiOnly) { // If we have an http writer, we can use the faster code path. Otherwise, // get a String out of the resource and write it. if (_httpWriter != null) { if (tabsPending) { OutputTabs(); } _httpWriter.WriteUTF8ResourceString(pv, offset, size, fAsciiOnly); } else { Write(StringResourceManager.ResourceToString(pv, offset, size)); } } public virtual void WriteEncodedUrl(String url) { int i = url.IndexOf('?'); if (i != -1) { WriteUrlEncodedString(url.Substring(0, i), false); Write(url.Substring(i)); } else { WriteUrlEncodedString(url, false); } } public virtual void WriteEncodedUrlParameter(String urlText) { WriteUrlEncodedString(urlText, true); } public virtual void WriteEncodedText(String text) { if (text == null) { throw new ArgumentNullException("text"); } const char NBSP = '\u00A0'; // When inner text is retrieved for a text control, is // decoded to 0x00A0 (code point for nbsp in Unicode). // HtmlEncode doesn't encode 0x00A0 to , we need to do it // manually here. int length = text.Length; int pos = 0; while (pos < length) { int nbsp = text.IndexOf(NBSP, pos); if (nbsp < 0) { HttpUtility.HtmlEncode(pos == 0 ? text : text.Substring(pos, length - pos), this); pos = length; } else { if (nbsp > pos) { HttpUtility.HtmlEncode(text.Substring(pos, nbsp - pos), this); } Write(" "); pos = nbsp + 1; } } } protected void WriteUrlEncodedString(String text, bool argument) { int length = text.Length; for (int i = 0; i < length; i++) { char ch = text[i]; if (HttpUtility.IsSafe(ch)) { Write(ch); } else if ( !argument && (ch == '/' || ch == ':' || ch == '#' || ch == ',' ) ) { Write(ch); } else if (ch == ' ' && argument) { Write('+'); } // for chars that their code number is less than 128 and have // not been handled above else if ((ch & 0xff80) == 0) { Write('%'); Write(HttpUtility.IntToHex((ch >> 4) & 0xf)); Write(HttpUtility.IntToHex((ch ) & 0xf)); } else { // VSWhidbey 448625: For DBCS characters, use UTF8 encoding // which can be handled by IIS5 and above. Write(HttpUtility.UrlEncodeNonAscii(Char.ToString(ch), Encoding.UTF8)); } } } internal void WriteHtmlAttributeEncode(string s) { if (_httpWriter == null) { HttpUtility.HtmlAttributeEncode(s, writer); } else { HttpUtility.HtmlAttributeEncodeInternal(s, _httpWriter); } } internal class Layout { private bool _wrap; private HorizontalAlign _align; /* public Layout(Layout currentLayout) { Align = currentLayout.Align; Wrap = currentLayout.Wrap; } */ public Layout(HorizontalAlign alignment, bool wrapping) { Align = alignment; Wrap = wrapping; } public bool Wrap { get { return _wrap; } set { _wrap = value; } } public HorizontalAlign Align { get { return _align; } set { _align = value; } } /* public bool Compare(Layout layout) { return Wrap == layout.Wrap && Align == layout.Align; } public void MergeWith(Layout layout) { if (Align == HorizontalAlign.NotSet) { Align = layout.Align; } if (Wrap) { Wrap = layout.Wrap; } } */ } private struct TagStackEntry { public HtmlTextWriterTag tagKey; public string endTagText; } private struct RenderAttribute { public string name; public string value; public HtmlTextWriterAttribute key; public bool encode; public bool isUrl; } private struct AttributeInformation { public string name; public bool isUrl; public bool encode; public AttributeInformation(string name, bool encode, bool isUrl) { this.name = name; this.encode = encode; this.isUrl = isUrl; } } private enum TagType { Inline, NonClosing, Other, } private struct TagInformation { public string name; public TagType tagType; public string closingTag; public TagInformation(string name, TagType tagType, string closingTag) { this.name = name; this.tagType = tagType; this.closingTag = closingTag; } } } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007.
Link Menu

This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- Animatable.cs
- SQLGuid.cs
- DecimalKeyFrameCollection.cs
- ColumnMapProcessor.cs
- ScriptDescriptor.cs
- BitConverter.cs
- ColorContext.cs
- CursorConverter.cs
- XmlHierarchyData.cs
- EncryptedPackage.cs
- PipelineDeploymentState.cs
- CopyOnWriteList.cs
- BinaryWriter.cs
- ConvertTextFrag.cs
- TreeViewHitTestInfo.cs
- MemberRestriction.cs
- SqlMethods.cs
- TextSpanModifier.cs
- ViewGenResults.cs
- RsaSecurityTokenAuthenticator.cs
- GeneralTransform3D.cs
- XmlElementAttribute.cs
- ObjectReferenceStack.cs
- BitmapDecoder.cs
- SQLInt16Storage.cs
- AspNetPartialTrustHelpers.cs
- PerformanceCounterManager.cs
- UpdateTranslator.cs
- DataError.cs
- ConfigurationElementCollection.cs
- StrokeCollection2.cs
- GlobalEventManager.cs
- OneWayBindingElement.cs
- AppDomainUnloadedException.cs
- GridViewSelectEventArgs.cs
- ExclusiveTcpTransportManager.cs
- TextBox.cs
- FeatureAttribute.cs
- XmlSigningNodeWriter.cs
- XamlToRtfParser.cs
- CommonGetThemePartSize.cs
- CheckBoxList.cs
- TCPListener.cs
- ParenthesizePropertyNameAttribute.cs
- SourceFileBuildProvider.cs
- HyperLinkColumn.cs
- CodeExpressionCollection.cs
- QilTernary.cs
- RegexCapture.cs
- TypeInfo.cs
- MaterialGroup.cs
- StatusBarItemAutomationPeer.cs
- MessageRpc.cs
- WindowsAuthenticationEventArgs.cs
- MediaPlayerState.cs
- ActivityXRefConverter.cs
- EventDescriptorCollection.cs
- ImageField.cs
- CustomExpressionEventArgs.cs
- ArglessEventHandlerProxy.cs
- FieldAccessException.cs
- RuntimeHandles.cs
- ThreadStartException.cs
- CompositionAdorner.cs
- MenuItemBindingCollection.cs
- AutomationPeer.cs
- BreakRecordTable.cs
- RowType.cs
- DefaultMemberAttribute.cs
- HttpVersion.cs
- ControlEvent.cs
- ToolTipAutomationPeer.cs
- WebPartConnectionCollection.cs
- NullableLongAverageAggregationOperator.cs
- SerializationAttributes.cs
- DbConnectionPoolOptions.cs
- Rfc2898DeriveBytes.cs
- LinkLabelLinkClickedEvent.cs
- PageAdapter.cs
- WriteableOnDemandStream.cs
- UnicastIPAddressInformationCollection.cs
- InternalCache.cs
- CompilerGlobalScopeAttribute.cs
- ByteConverter.cs
- TextBounds.cs
- Exceptions.cs
- ReferenceSchema.cs
- ColorMatrix.cs
- SByteConverter.cs
- DesignerDataSchemaClass.cs
- ToolStripDropTargetManager.cs
- RightsManagementErrorHandler.cs
- TypeConverterAttribute.cs
- ReadOnlyAttribute.cs
- Expression.cs
- BaseTemplateBuildProvider.cs
- EdmProperty.cs
- unsafeIndexingFilterStream.cs
- Int16Storage.cs
- VisualTarget.cs