在MonoRail中我们可以定义一些可重用的组件,在其他需要使用的页面引入这个组件就可以了。有点相当于.NET中的自定义控件,可以节约代码,方便开发,提高重用性。
在MonoRail中把这一功能叫做ViewComponent,下面就来具体看看它的使用方法:
ViewComponent可以使用现成的view,可以给父view发送数据,也支持参数输入和内部多节的方式
1、生成ViewComponent类:
要生成自己的ViewComponet必须从抽象类ViewComponent继承,继承后有三个方法可以被覆盖:
Initialize:初始化,可以在这个方法中接收传递的参数
Render:渲染实际的显示内容
SupportsSection:指定这个组件可以支持哪些子节点
最简单的一个ViewComponent:
public class HeaderComponent : ViewComponent
{
}
当使用这个组件时会直接渲染views下的components/headercomponent/default.vm文件
当然和Controller一样,我们也可以指定一个渲染的vm文件:
1 2 3 4 5 6 7 8 9 | using Castle.MonoRail.Framework; public class HeaderComponent : ViewComponent { public override void Render() { RenderView( "otherview" ); } } |
这样的话就会使用views下的components/headercomponent/otherview.vm文件
2、使用ViewComponent组件
生成组件之后,接下来就要看看如何使用它。主要的使用方式有两种:普通方式和嵌套内容的方式,使用时都是直接把类名作为组件名称来使用的
a、普通方式:
使用component关键字来使用
b、嵌套内容的方式:
C#代码:
1 2 3 4 5 6 7 8 9 10 11 12 | public class BlockViewComponent2 : ViewComponent { public BlockViewComponent2() { } public override void Render() { Context.ContextVars[ "it" ] = "GSpring" ; Context.RenderBody(); } } |
vm代码:
inner content $it
#end
调用之后,显示在页面上的内容就是:
嵌套方式主要就是使用关键字:blockcomponent
Context.RenderBody()方法是用来渲染内容的,可以同时调用多次,那么所包含的内容就会显示多次
3、使用参数
正如.NET的自定义控件一样,MonoRail中的自定义控件也可以从外部接收一些参数,比如显示的颜色、大小、其他参数等。
使用ComponentParams属性在Initialize方法中来接收:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | using Castle.MonoRail.Framework; public class TableComponent : ViewComponent { private ICollection elements; private object border; private string style; private object cellpadding; private object cellspacing; public override void Initialize() { elements = (ICollection) ComponentParams[ "elements" ]; border = ComponentParams[ "border" ]; style = (String) ComponentParams[ "style" ]; cellpadding = ComponentParams[ "cellpadding" ]; cellspacing = ComponentParams[ "cellspacing" ]; base .Initialize(); } |
调用的时候,就可以写成这样:
#end
或:
4、嵌套子节点的使用
在ViewComponet中还可以定义多个子节点,在一些复杂的情况下比较方便,看下面的一个实例:
Contoller代码:
1 2 3 4 5 6 7 8 9 10 | public void Default() { ArrayList items = new ArrayList(); items.Add( "项目1" ); items.Add( "项目2" ); items.Add( "项目3" ); PropertyBag.Add( "items" , items); } |
ViewCompoent代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 | public class TableComponent : ViewComponent { private ICollection elements; private object border; private string style; private object cellpadding; private object cellspacing; public override void Initialize() { elements = (ICollection)ComponentParams[ "elements" ]; border = ComponentParams[ "border" ]; style = (String)ComponentParams[ "style" ]; cellpadding = ComponentParams[ "cellpadding" ]; cellspacing = ComponentParams[ "cellspacing" ]; base .Initialize(); } public override void Render() { RenderText( String.Format( "<table border=\"{0}\" style=\"{1}\" cellpadding=\"{2}\" cellspacing=\"{3}\">" , border, style, cellpadding, cellspacing)); if (Context.HasSection( "colheaders" )) { Context.RenderSection( "colheaders" ); } if (elements != null ) { int index = 0; foreach ( object item in elements) { PropertyBag[ "index" ] = ++index; PropertyBag[ "item" ] = item; if (Context.HasSection( "altitem" ) && index % 2 != 0) { Context.RenderSection( "altitem" ); } else { Context.RenderSection( "item" ); } } } RenderText( "</table>" ); } public override bool SupportsSection( string name) { return name == "colheaders" || name == "item" || name == "altitem" ; } } |
vm代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | #blockcomponent(TableComponent with "elements=$items") #colheaders <tr> <th> </th> <th>Element</th> </tr> #end #item <tr> <td>$index</td> <td>$item</td> </tr> #end #altitem <tr> <td style= " padding: 0px; color: rgb(0, 0, 255);" >>$index</td> <td style= " padding: 0px; color: rgb(0, 0, 255);" >>$item</td> </tr> #end #end |
显示的效果,如下图所示:
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步