rendered paste bodyusing System;
using System.Diagnostics;
using System.IO;
using System.Text;
using System.Text.RegularExpressions;
using System.Web.UI;
using System.Web.UI.HtmlControls;
using System.Web.UI.WebControls;
namespace Frost
{
/// <summary>
///
/// </summary>
public class Xhtml : Page
{
#region Private Variables
private string _xhtml;
private string _language;
private XHtmlFormat _xhtmlFormat;
private Encoding _encoding;
private bool _xmlCDATA;
#endregion
#region Constructor
/// <summary>
/// Default Constructor.
/// </summary>
public Xhtml( )
{
_xhtml = "";
_xhtmlFormat = XHtmlFormat.XHtml10_Strict;
_language = "en-GB";
_xmlCDATA = false;
}
#endregion
#region Overriding Methods
/// <summary>
///
/// </summary>
/// <param name="writer"></param>
protected override void Render( HtmlTextWriter writer )
{
StringWriter sw = new StringWriter( );
HtmlTextWriter output = new HtmlTextWriter( sw );
base.Render( output );
output.Close( );
_xhtml = sw.GetStringBuilder( ).ToString( );
ReplaceDocType( );
switch ( _xhtmlFormat )
{
case XHtmlFormat.XHtml10_Frameset:
ConvertToXHtmlFrameset( );
break;
case XHtmlFormat.XHtml10_Strict:
ConvertToXHtmlStrict( );
break;
case XHtmlFormat.XHtml10_Transitional:
ConvertToXHtmlTransitional( );
break;
}
writer.Write( _xhtml );
}
#endregion
#region Private Methods
/// <summary>
///
/// </summary>
/// <param name="TagName"></param>
private void AddSelfClose( string TagName )
{
int start = 0;
int pos = 0;
while ( pos >= 0 )
{
string search = "<" + TagName;
pos = _xhtml.IndexOf( search, start );
if ( pos > 0 )
{
start = pos + 1;
int end = _xhtml.IndexOf( ">", start );
if ( _xhtml[ end - 1 ] != '/' )
{
_xhtml = _xhtml.Insert( end, "/>" );
}
}
}
}
/// <summary>
///
/// </summary>
private void ConvertToLowerCase( )
{
_xhtml = Regex.Replace( _xhtml, "<(/?)([a-zA-Z]+)(\\s*)>", new MatchEvaluator( SingleTagToLowerCase ), RegexOptions.IgnoreCase );
_xhtml = Regex.Replace( _xhtml, "<(/?)([a-zA-Z0-9]+)[ ]*(.*?)>", new MatchEvaluator( PropertiesToLowerCase ), RegexOptions.IgnoreCase );
_xhtml = Regex.Replace( _xhtml, "<([a-zA-Z0-9]+)(\\s+[a-zA-Z]+)(=\".+?>)", new MatchEvaluator( PropertiesToLowerCase ), RegexOptions.IgnoreCase );
}
/// <summary>
///
/// </summary>
private void ConvertToXHtmlFrameset( )
{
ConvertToLowerCase( );
AddSelfClose( "meta" );
FixHtml( );
}
/// <summary>
///
/// </summary>
private void ConvertToXHtmlStrict( )
{
ConvertToLowerCase( );
AddSelfClose( "meta" );
AddSelfClose( "link" );
AddSelfClose( "img" );
AddSelfClose( "hr" );
FixScript( );
RemoveAttribute( "form", "name" );
FixInput( );
FixBr( );
FixStyle( );
FixHtml( );
MaskScript( );
}
/// <summary>
///
/// </summary>
private void ConvertToXHtmlTransitional( )
{
ConvertToLowerCase( );
AddSelfClose( "meta" );
AddSelfClose( "link" );
AddSelfClose( "img" );
AddSelfClose( "hr" );
FixScript( );
FixBr( );
FixStyle( );
FixHtml( );
}
/// <summary>
///
/// </summary>
private void FixBr( )
{
_xhtml = _xhtml.Replace( "<br>", "<br />" );
}
/// <summary>
///
/// </summary>
private void FixHtml( )
{
_xhtml = Regex.Replace( _xhtml, "<html>", new MatchEvaluator( HTMLTag ), RegexOptions.IgnoreCase );
}
/// <summary>
///
/// </summary>
private void FixInput( )
{
int start = 0;
int pos = 0;
while ( pos >= 0 )
{
string search = "<input type=\"hidden\"";
pos = _xhtml.IndexOf(search, start);
if(pos > 0)
{
start = pos + search .Length;
_xhtml = _xhtml.Insert(pos, "<pre>");
int end = _xhtml.IndexOf(">", start);
if(end > 0)
{
_xhtml = _xhtml.Insert(end + 1, "</pre>");
}
}
}
}
/// <summary>
///
/// </summary>
private void FixScript( )
{
_xhtml = _xhtml.Replace( "<script language=\"javascript\">", "<script type=\"text/javascript\">" );
}
/// <summary>
///
/// </summary>
private void FixStyle( )
{
_xhtml = Regex.Replace( _xhtml, @"(<style[^<]*>){1}(?(?=\s*<!--)(\s*<!--)(\s*.*?)(//\s*-->)|(\s*.*?))\s*(</style>){1}", new MatchEvaluator( FixStyleAndScript ), RegexOptions.IgnoreCase | RegexOptions.Singleline );
}
/// <summary>
///
/// </summary>
/// <param name="m"></param>
/// <returns></returns>
private string FixStyleAndScript( Match m )
{
string ret = "";
string st;
string ed;
if ( _xmlCDATA )
{
st = "\r\n<![CDATA[\r\n";
ed = "\r\n]]>\r\n";
}
else
{
st = "\r\n<!-\r\n";
ed = "\r\n//-->\r\n";
}
if ( m.Groups[ 2 ].ToString( ).Trim( ) == "" && m.Groups[ 4 ].ToString( ).Trim( ) == "" )
{
st = "";
ed = "";
}
ret = m.Groups[ 1 ].ToString( ) + st;
ret += m.Groups[ 2 ].ToString( ) + m.Groups[ 4 ].ToString( ) + ed + m.Groups[ 5 ].ToString( );
return ret;
}
/// <summary>
///
/// </summary>
/// <param name="m"></param>
/// <returns></returns>
private string HTMLTag( Match m )
{
return "<html xmlns=\"http://www.w3.org/1999/xhtml\" xml:lang=\"" + _language + "\">";
}
/// <summary>
///
/// </summary>
private void MaskScript( )
{
_xhtml = Regex.Replace( _xhtml, @"(<script[^<]*>){1}(?(?=\s*<!--)(\s*<!--)(\s*.*?)(//\s*-->)|(\s*.*?))\s*(</script>){1}", new MatchEvaluator( FixStyleAndScript ), RegexOptions.IgnoreCase | RegexOptions.Singleline );
}
/// <summary>
///
/// </summary>
/// <param name="m"></param>
/// <returns></returns>
private string NextProperty( Match m )
{
string replace = m.Groups[ 1 ].ToString( ) + m.Groups[ 2 ].ToString( ).ToLower( );
if ( Regex.Match( m.Groups[ 3 ].ToString( ), "(.*?\")(\\s+\\w+)(=\".+>)", RegexOptions.IgnoreCase ).Success && m.Groups[ 3 ].ToString( ).IndexOf( "__VIEWSTATE" ) == -1 )
{
Debug.WriteLine( "Match OK", "NextProperty" );
replace += Regex.Replace( m.Groups[ 3 ].ToString( ), "(.*?\")(\\s+\\w+)(=\".+>)", new MatchEvaluator( NextProperty ), RegexOptions.IgnoreCase );
}
else
{
Debug.WriteLine( "Match Not OK", "NextProperty" );
replace += m.Groups[ 3 ].ToString( );
}
return replace;
}
/// <summary>
///
/// </summary>
/// <param name="m"></param>
/// <returns></returns>
private string PropertiesToLowerCase( Match m )
{
string replace = "<" + m.Groups[ 1 ].ToString( ) + m.Groups[ 2 ].ToString( ).ToLower( );
if ( Regex.Match( m.Groups[ 3 ].ToString( ), "(.*?\")(\\s+\\w+)(=\".+>)", RegexOptions.IgnoreCase ).Success )
{
replace += Regex.Replace( m.Groups[ 3 ].ToString( ), "(.*?\")(\\s+\\w+)(=\".+>)", new MatchEvaluator( NextProperty ), RegexOptions.IgnoreCase );
}
else
{
replace += m.Groups[ 3 ].ToString( );
}
return replace;
}
/// <summary>
///
/// </summary>
/// <param name="TagName"></param>
/// <param name="AttributeName"></param>
private void RemoveAttribute( string TagName, string AttributeName )
{
int start = 0;
int pos = 0;
while ( pos >= 0 )
{
string search = "<" + TagName + "" + AttributeName + "=\"";
pos = _xhtml.IndexOf( search, start );
if ( pos > 0 )
{
start = pos + TagName.Length + 1;
int end = _xhtml.IndexOf( "\"", pos + search.Length + 1 );
if ( end > 0 )
{
_xhtml = _xhtml.Remove( start, end - start + 1 );
}
}
}
}
/// <summary>
///
/// </summary>
private void ReplaceDocType( )
{
int start = _xhtml.IndexOf( "<!DOCTYPE", 0 );
if(start > 0)
{
int end = _xhtml.IndexOf(">", start + 1);
if(end > 0)
{
_xhtml = _xhtml.Remove(start, end - start + 1);
switch(_xhtmlFormat)
{
case XHtmlFormat.XHtml10_Frameset:
_xhtml = _xhtml.Insert(0, "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Frameset//EN\"\"http://www.w3.org/TR/xhtml1/DTD/xhtml1-frameset.dtd\">");
break;
case XHtmlFormat.XHtml10_Strict:
_xhtml = _xhtml.Insert(0, "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Strict//EN\"\"http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd\">");
break;
case XHtmlFormat.XHtml10_Transitional:
_xhtml = _xhtml.Insert(0, "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\"\"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">");
break;
}
}
}
}
/// <summary>
///
/// </summary>
/// <param name="m"></param>
/// <returns></returns>
private string SingleTagToLowerCase(Match m)
{
if(m.Groups[3].ToString().Trim() == string.Empty)
return "<" + m.Groups[1].ToString().ToLower() + m.Groups[2].ToString().ToLower() + ">";
else
return "<" + m.Groups[1].ToString().ToLower() + m.Groups[2].ToString().ToLower() + "" + m.Groups[3].ToString() + ">";
}
/// <summary>
///
/// </summary>
/// <param name="m"></param>
/// <returns></returns>
private string ToLowerCase( Match m )
{
return m.ToString( ).ToLower( );
}
#endregion
#region Properties
/// <summary>
///
/// </summary>
public XHtmlFormat XHTMLFormat
{
get { return _xhtmlFormat; }
set { _xhtmlFormat = value; }
}
/// <summary>
///
/// </summary>
public Encoding Encoding
{
get { return _encoding; }
set { _encoding = value; }
}
/// <summary>
///
/// </summary>
public string Language
{
get { return _language; }
set { _language = value; }
}
/// <summary>
///
/// </summary>
public bool XMLCDATA
{
get { return _xmlCDATA; }
set { _xmlCDATA = value; }
}
#endregion
}
}