没脾气2x:
CNDEV UBB C# 目前俺写的烂代码公开:
[阅读: 768] 2007-04-09 16:54:45
[CODE=C#]
public static class Encoder
{
static object lockUsedDict = new object();
static private TagParseDict m_ParseDict = null;
static TagParseDict GetParseDict()
{
lock ( lockUsedDict )
{
if ( m_ParseDict == null )
{
TagParseDict dict = new TagParseDict();
dict.Add( new TagLinkUrl( "url" ) );
dict.Add( new TagImg( "img" ) );
dict.Add( new TagLinkEmail( "email" ) );
dict.Add( new TagFontSizeCustom( "size" ) );
dict.Add( new TagSimple( "b" ) );
dict.Add( new TagSimple( "i" ) );
dict.Add( new TagSimple( "u" ) );
dict.Add( new TagFontStrike( "s" ) );
dict.Add( new TagFontBox( "box" ) );
dict.Add( new TagSimple( "center" ) );
dict.Add( new TagAlignSimple( "right", "right" ) );
dict.Add( new TagAlignSimple( "left", "left" ) );
dict.Add( new TagFontColorSimple( "green", "#009900" ) );
dict.Add( new TagFontColorSimple( "red", "#ff0000" ) );
dict.Add( new TagFontColorSimple( "blue", "#000099" ) );
dict.Add( new TagFontColorSimple( "gray", "#999999" ) );
dict.Add( new TagFontColorCustom( "color" ) );
dict.Add( new TagCode( "code" ) );
dict.Add( new TagMarqueeFly( "fly" ) );
dict.Add( new TagMarqueeMove( "move" ) );
dict.Add( new TagMediaWMP( "mp" ) );
dict.Add( new TagMediaWMP( "wmp" ) );
dict.Add( new TagMediaRM( "rm" ) );
dict.Add( new TagMediaRM( "rmvb" ) );
dict.Add( new TagMediaQT( "qt" ) );
dict.Add( new TagMediaFlash( "flash" ) );
dict.Add( new TagPlainText( "pre" ) );
dict.Add( new TagPlainText( "plain" ) );
m_ParseDict = dict;
}
}
return m_ParseDict;
}
static readonly int MaxUBBStoneLength = 1000;
static readonly string UBBErrorContainer = "
{0}";
static public string HtmlFromUBBCode( string strInput )
{
TagParseDict dictParse = GetParseDict();
if ( String.IsNullOrEmpty( strInput ) )
{
return String.Empty;
}
System.IO.StringWriter writer = new System.IO.StringWriter();
System.Collections.Generic.Stack
tagstack = new System.Collections.Generic.Stack();
int posNext = 0;
bool isInStone = false;
StoneItem tagLast = null;
while ( posNext < strInput.Length )
{
// 搜索 [ 开始的位置
int pos;
// IF 现在是否在“使用内容的Tag”的内容区中
if ( tagLast != null && tagLast.isContentUseInTag )
{
// Y 在“使用内容的Tag的内容区”中
pos = strInput.IndexOf( "[/" + tagLast.tagName + "]", posNext, StringComparison.CurrentCultureIgnoreCase );
// 容错: 开始没有对应的结束(对于使用Content的Tag)
if ( pos < 0 )
{
// 如果没有搜索到上一个需关闭 tag 的未关闭,则将勿略 tag 开始以后的所有内容
tagstack.Pop();
if ( tagstack.Count > 0 )
{
tagLast = tagstack.Peek();
}
else
{
tagLast = null;
}
posNext = strInput.Length;
continue;
}
}
else
{
// 不在内容区中
pos = strInput.IndexOf( '[', posNext );
}
// pos 是找到的 [ 的位置(或者是找到的“使用内容的Tag”的末尾半闭符 [/TAGNAME])
if ( pos >= posNext )
{
// 找到 stone 的前缀 [
// 将 stone 前面的内容适当处理
if ( tagLast != null && tagLast.isContentUseInTag )
{
tagLast.tagContent = strInput.Substring( posNext, pos - posNext );
}
else
{
writer.Write( Encoder.HtmlBreak( strInput.Substring( posNext, pos - posNext ) ) );
}
int posStoneStart = pos;
int posStoneEnd;
int posStoneSearch;
int posStoneSearchStart = posStoneStart + 1;
bool isInQuote = false;
bool isFinishStone = false;
while ( true )
{
posStoneSearch = strInput.IndexOfAny( new char[] { ']', '\'', '"' }, posStoneSearchStart );
if ( posStoneSearch < 0 || posStoneSearch - posStoneSearchStart > MaxUBBStoneLength )
{
posStoneSearch = -1;
// 容错: [ 没有对应的 ]
// 容错: [ 里面内容太多(超过 MaxUBBStoneLength)
// 进入 stone 后没有任何 ] 那么把它当成一个普能
isFinishStone = false;
break;
}
else if ( strInput[posStoneSearch] == '\'' || strInput[posStoneSearch] == '"' )
{
// 容错: [ 中的 ' 或 " 不配对
char quote = strInput[posStoneSearch];
isInQuote = true;
posStoneSearchStart = posStoneSearch + 1;
posStoneSearch = strInput.IndexOf( quote, posStoneSearchStart );
if ( posStoneSearch < 0 )
{
isFinishStone = false;
break;
}
posStoneSearchStart = posStoneSearch + 1;
isInQuote = false;
}
else
{
// 防止空
if ( posStoneSearch > posStoneStart + 1 )
{
isFinishStone = true;
}
else
{
posStoneSearchStart = posStoneSearch + 1;
isFinishStone = false;
}
break;
}
}
if ( isFinishStone )
{
// ]
posStoneEnd = posStoneSearch;
posNext = posStoneEnd + 1;
// 分析 stone
bool isStoneTagEnd = false;
string strInStone = strInput.Substring( posStoneStart + 1, posStoneEnd - (posStoneStart + 1) ).Trim();
if ( strInStone.StartsWith( "/" ) )
{
isStoneTagEnd = true;
strInStone = strInStone.Remove( 0, 1 );
}
string strStoneName;
string strStoneValuesContent = String.Empty;
string strStoneAttribsContent = String.Empty;
// 在 strInStone(stone 的字符串内部)取得 stoneName
int posStoneNameEnd = strInStone.IndexOfAny( new char[] { ' ', '=' } );
if ( posStoneNameEnd < 0 )
{
strStoneName = strInStone.ToLower().Trim();
strStoneValuesContent = String.Empty;
strStoneAttribsContent = String.Empty;
}
else
{
strStoneName = strInStone.Substring( 0, posStoneNameEnd ).ToLower().Trim();
if ( strInStone[posStoneNameEnd] == '=' )
{
strStoneValuesContent = strInStone.Substring( posStoneNameEnd + 1 ).Trim();
}
else
{
strStoneAttribsContent = strInStone.Substring( posStoneNameEnd + 1 ).Trim();
}
}
// 对 stone 是 TagStart 还是 TagEnd 分别处理
if ( !isStoneTagEnd )
{
if ( dictParse.Contains( strStoneName.ToLower().Trim() ) )
{
TagParseItem parse = dictParse[strStoneName.ToLower().Trim()];
StoneItem tag = new StoneItem();
tag.tagName = strStoneName;
tag.tagAttributes = strStoneAttribsContent;
tag.tagValues = strStoneValuesContent;
writer.Write( parse.ProcessTagStart( tag ) );
tagLast = tag;
tagstack.Push( tag );
}
else
{
// 容错: StoneName 找不到
writer.Write(
String.Format(
UBBErrorContainer,
Nox.Common.Encoder.HtmlBreak( strInput.Substring( posStoneStart, posStoneEnd - posStoneStart + 1 ) )
)
);
}
}
else
{
if ( tagLast != null && strStoneName.Equals( tagLast.tagName, StringComparison.CurrentCultureIgnoreCase ) )
{
StoneItem tag = tagstack.Pop();
// 因为在 tagstack 中存在的都是 dictParse 经判断的 stone(上面的 if 语句判定的推论)
// 所以这里可以直接用 dictParse.IndexOf 而不需要使用 dictParse.Contains
TagParseItem parse = dictParse[strStoneName];
writer.Write( parse.ProcessTagEnd( tag ) );
if ( tagstack.Count == 0 )
{
tagLast = null;
}
else
{
tagLast = tagstack.Peek();
}
}
else
{
// 容错: 结束没有对应的开始
writer.Write( "[/{0}]", Encoder.Html( strInStone ) );
}
}
}
else // if ( !isFinishStone )
{
// 容错: [ 没有对应的 ] 则当作没有这个
posNext = posStoneSearchStart;
writer.Write( "{0}", Encoder.Html( strInput.Substring( posStoneStart, posStoneSearchStart - posStoneStart ) ) );
pos = -1;
}
}
if ( pos < 0 )
{
break;
}
}
if ( posNext < strInput.Length )
{
// 如果没有搜索到 [ ,那么说后面没有 stone 了
// 处理后面的文本
if ( tagLast != null && tagLast.isContentUseInTag )
{
tagLast.tagContent = strInput.Substring( posNext );
}
else
{
writer.Write( Encoder.HtmlBreak( strInput.Substring( posNext ) ) );
}
posNext = strInput.Length;
}
// 容错: 开始没有对应的结束"
if ( tagstack.Count > 0 )
{
for ( int i = tagstack.Count - 1; i >= 0; i-- )
{
StoneItem tag = tagstack.Pop();
TagParseItem parse = dictParse[tag.tagName];
writer.Write( parse.ProcessTagEnd( tag ) );
}
}
return writer.ToString();
}
}
[/CODE]
这破函数太长了,以后可能的话得改改 Notemper2x 3.1 ( ̄ε( ̄#)
没脾气2x 之 个人综合篇:
http://notemper2x.cndev.org/
我的 panoramio 相册:
http://panoramio.com/user/zhaixudong
我的 flickr相册:
http://www.flickr.com/photos/notemper2x/


QQ号20250出售,售价400,000元整(5位、皇冠80级、VIP7)a