将 Usercontrol 转换为 WebControl






2.08/5 (6投票s)
2004年8月11日

72827

614
你创建了一个具有 HTML 布局的漂亮的 UserControl,但希望将其用作服务器控件。此宏将为你生成实例化和渲染代码。
引言
你是否曾经编写了一个不错的 UserControl,并希望将其迁移到 WebControl?那么你就会知道你需要自己编写大量的渲染和初始化代码。使用此宏,这些代码将从你创建的 .ascx 文件中生成。
例如,如果你有以下代码
那么此宏将在输出窗口中输出以下行
然后你只需要将代码复制到代码隐藏文件中,更改继承关系,瞧,一个 WebControl 就完成了。
该宏
Sub GenerateWebcontrolCode()
Dim str As String = ""
Dim createCC As String = ""
Dim renderCC As String = ""
Dim attribsCC As String = ""
Dim selection As TextSelection = DTE.ActiveDocument.Selection()
selection.SelectAll()
Dim theText As String = selection.Text
'all <asp:Label like tags and id's
Dim r As New Regex("\<(?<tag>\w*):(?<type>\w*)" & _
"(.\n?)*?id=\""?(?<id>\w*)\""?(.\n?)*?>", RegexOptions.IgnoreCase)
Dim matches As MatchCollection = r.Matches(theText)
Dim m As Match
'set the startindex to position after the last <%@ register tag!!
Dim startindex As Integer = 0
Dim matchRegistertags As Match = Regex.Match(theText, _
"<%@.*?>", RegexOptions.RightToLeft)
startindex = matchRegistertags.Index + matchRegistertags.Length
If (startindex < 0) Then
startindex = 0
End If
For Each m In matches
'only start again after endtag (templated controls will not work!!)
If m.Index > startindex Then
Dim tp As String = m.Groups("type").Value
Dim id As String = m.Groups("id").Value
Dim tag As String = m.Groups("tag").Value
'the stuff for the render override
'Get the html in before the control
'and write this to the HTMLwriter
Dim htmlstr As String = _
theText.Substring(startindex, m.Index - startindex)
htmlstr = htmlstr.Replace("""", """""")
renderCC += "writer.Write(@""" + htmlstr + """);" + vbCrLf
renderCC += id + ".RenderControl(writer);" + vbCrLf
'Set the index to the position of the endtag (if available,
'otherwise control is closed with />
startindex = m.Index + m.Length
Dim endtag As String = "</" + tag + ":" + tp + ">"
Dim inext2 As Integer = theText.IndexOf(endtag, startindex)
If inext2 <> -1 Then
startindex = inext2 + endtag.Length
End If
' the stuff for the init procedures make sure you add this to
createCC += id + " = new " + tp + "();" + vbCrLf
'Add attributes to the object.
'Only attibutes assigned within the first tag no
'templated controls or default properties are set
Dim r2 As New Regex("(?<prop>\w*)=\""?(?<value>\w*)\""?", _
RegexOptions.IgnoreCase)
Dim ms2 As MatchCollection = r2.Matches(m.Value)
Dim m2 As Match
For Each m2 In ms2
Dim prop As String = m2.Groups("prop").Value
Dim val As String = m2.Groups("value").Value
If prop.ToLower() <> "runat" Then
createCC += id + "." + prop + " = """ + val + """;" + vbCrLf
End If
Next
'add the control to the control collection
createCC += "this.Controls.Add(" + id + ");" + vbCrLf + vbCrLf
End If
Next
'render the final html after the last control
Dim htmlstr2 As String = theText.Substring(startindex, _
theText.Length - startindex)
htmlstr2.Replace("""", """""")
renderCC += "writer.Write(@""" + htmlstr2 + """);" + vbCrLf
'now show the text om the output window
Dim win As Window = DTE.Windows.Item(EnvDTE.Constants.vsWindowKindOutput)
Dim OWp As OutputWindowPane = win.Object.OutputWindowPanes.Item(1)
OWp.Clear()
OWp.Activate()
OWp.OutputString("-----------------" + vbCrLf)
OWp.OutputString("Add this to the Init procedure" & _
" (before any events are assigned)" + vbCrLf)
OWp.OutputString("TODO check type casing and property types," & _
" dynamically load templated elements" + vbCrLf)
OWp.OutputString("-----------------" + vbCrLf)
OWp.OutputString(createCC)
OWp.OutputString("-----------------" + vbCrLf)
OWp.OutputString("Add this to the render function" + vbCrLf)
OWp.OutputString("-----------------" + vbCrLf)
OWp.OutputString(renderCC)
OWp.TextDocument.Selection.GotoLine(OWp.TextDocument.EndPoint().Line())
DTE.ExecuteCommand("View.Output")
End Sub
只需将代码复制粘贴到 .ascx.cs 文件中,并从 WebControl
而不是 UserControl
继承。(或者,如果你愿意,可以创建一个新的类文件,其中包含所有代码。)
不幸的是,你必须检查类型的命名大小写,因为如果在 ascx 文件中存在 <asp:button
,则类型将是 button(小写),还要检查分配的参数的类型。(假设 String
类型,参见 Button1.BorderWidth = "4px"
;当然,这应该只是 4
。)
祝你好运,希望这能节省一些打字。
问候 Rooc。