代码生成工具之界面快速生成
界面开发,无论对于Web开发,还是Winform开发,都需要耗费一定的时间,特别对于一个数据库字段比较多的界面,一般就需要在编辑界面上摆的更多的控件来做数据显示,每次碰到这个,都有点头痛,反复的机械操作让人挺累,也很烦,但是又必须这样做。
由于数据库字段和界面的排版都有一定的关联关系,因此可以通过代码生成工具Database2Sharp的数据库元数据,包含表名称、备注信息、字段列表,以及每个字段的名称、备注、类型等信息,构造一个基础的界面,把重复机械的部分给快速完成,这就是我所说的界面快速生成。当然,对于精致的界面,机械的生成肯定不能满足我们的需要,因此真正的界面需要在这个基础上修改完善一下,但是由于重复劳动部分,已经给工具处理掉了,因此,界面开发效率会大大提高。
1、基于Web界面的快速生成
基于EnterpriseLibray架构的代码生成,除了可以生成传统的业务层、数据访问层、数据访问接口层、实体层外,还同时生成了Web界面工程,Web界面工程已经添加了相关的引用程序集及必须的控件,生成后即可编译运行,一些表字段设计合理的话,甚至不用修改一行代码就能直接使用,如下所示。
生成后的项目界面截图如下所示。
以下是TB_ItemDetail表生成的界面,没有修改过任何东西,列表页面呈现的效果。
其中编辑及查看页面也生成了,直接单击连接就可以看到效果,如下图所示。
这些效果是很基本的界面布局了,如果需要更好看的,可以根据需要调整下每行的数量,以及显示方式。这样的效果,虽然不算最好看,但是已经帮我们把界面元素弄起来了,我们后面的工作就很好开展,不用再重复添加每个字段对应的控件布局信息了。具体的代码是标准的HTML控件代码如下所示。
<%@ Page Language="C#" MasterPageFile="~/MasterPage.master" AutoEventWireup="true" Inherits="Pages_ItemDetail_EditItemDetail" Codebehind="EditItemDetail.aspx.cs" %> <asp:Content ID="Content1" ContentPlaceHolderID="ContentPlaceHolder1" runat="Server"> <h3 id="h_title" align="center" runat="server">编辑备件信息表 </h3> <table class="formitem" cellspacing="1" cellpadding="0" align="Center" border="0" style="border-width: 0px; width: 98%;"> <caption>基本信息</caption> <tr style="width: 100%;"> <th align="left" style="width: 20%;"> 备件编号 : </th> <td style="width: 80%;" colspan="3"> <asp:TextBox ID="txtItemNo" runat="server" Width="250px" MaxLength="100"></asp:TextBox> </td> </tr> <tr style="width: 100%;"> <th align="left" style="width: 20%;"> 备件名称 : </th> <td style="width: 80%;" colspan="3"> <asp:TextBox ID="txtItemName" runat="server" Width="250px" MaxLength="100"></asp:TextBox> </td> </tr> <tr style="width: 100%;"> <th align="left" style="width: 20%;"> 供货商 : </th> <td style="width: 80%;" colspan="3"> <asp:TextBox ID="txtManufacture" runat="server" Width="250px" MaxLength="100"></asp:TextBox> </td> </tr>
...............
当然后台代码的保存及赋值显示,肯定是少不了的了,这些也是根据我的框架代码生成的,应该来说是很有用的。
public partial class Pages_ItemDetail_EditItemDetail : BasePage { protected override void OnInit(EventArgs e) { base.OnInit(e); this.IsFunctionControl = true; this.FunctionID = "ItemDetail/Edit"; } private void BindData() { try { string id = Request.QueryString["ID"]; if(!string.IsNullOrEmpty(id)) { ItemDetailInfo info = BLLFactory<ItemDetail>.Instance.FindByID(id); if(info != null) { this.txtItemNo.Text = info.ItemNo; this.txtItemName.Text = info.ItemName; this.txtManufacture.Text = info.Manufacture; this.txtMapNo.Text = info.MapNo; this.txtSpecification.Text = info.Specification; this.txtMaterial.Text = info.Material; this.txtItemBigType.Text = info.ItemBigType; this.txtItemType.Text = info.ItemType; this.txtUnit.Text = info.Unit; this.txtPrice.Text = info.Price.ToString(); this.txtSource.Text = info.Source; this.txtStoragePos.Text = info.StoragePos; this.txtUsagePos.Text = info.UsagePos; this.txtNote.Text = info.Note; this.txtWareHouse.Text = info.WareHouse; this.txtDept.Text = info.Dept; } } } catch(Exception ex) { Helper.ShowError(this, ex, false); return; } } protected void Page_Load(object sender, EventArgs e) { if(!this.IsPostBack) { BindData(); } } /// <summary> /// 获取数据 /// </summary> private ItemDetailInfo SetData(ItemDetailInfo info) { info.ItemNo = this.txtItemNo.Text; info.ItemName = this.txtItemName.Text; info.Manufacture = this.txtManufacture.Text; info.MapNo = this.txtMapNo.Text; info.Specification = this.txtSpecification.Text; info.Material = this.txtMaterial.Text; info.ItemBigType = this.txtItemBigType.Text; info.ItemType = this.txtItemType.Text; info.Unit = this.txtUnit.Text; info.Price = Helper.SafeConvertDecimal(this.txtPrice.Text); info.Source = this.txtSource.Text; info.StoragePos = this.txtStoragePos.Text; info.UsagePos = this.txtUsagePos.Text; info.Note = this.txtNote.Text; info.WareHouse = this.txtWareHouse.Text; info.Dept = this.txtDept.Text; return info; } protected void imgSubmit_Click(object sender, ImageClickEventArgs e) { try { string id = Request.QueryString["ID"]; if(string.IsNullOrEmpty(id)) { ItemDetailInfo info = new ItemDetailInfo(); SetData(info); BLLFactory<ItemDetail>.Instance.Insert(info); } else { ItemDetailInfo info = BLLFactory<ItemDetail>.Instance.FindByID(id); if(info != null) { SetData(info); BLLFactory<ItemDetail>.Instance.Update(info, id); } } } catch(Exception ex) { Helper.ShowError(this, ex, false); return; } Response.Redirect("ListItemDetail.aspx"); } protected void imgBack_Click(object sender, ImageClickEventArgs e) { Response.Redirect("ListItemDetail.aspx"); } }
有了这些智能的界面生成,界面开发其实是一件不再枯燥的事情,节省更多的时间,做更有意义的事情。
2、基于DevExpress的Winform界面快速生成
除了Web的界面开发,Winform的界面开发,当然也很重要,枯燥的事情一样可以交给代码生成工具Database2Sharp进行生成,不需要让人工反复的做这些无用功,或者是技术含量不太高的东西。
上面Web界面工程,我是采用SQLServer的数据库进行生成代码的,这个例子,我们介绍一下Oracle数据库的生成方式,其实这个代码生成工具,对应用什么数据库不重要,都会很好的给你生成相关的界面信息,不管你是用SQLServer还是Oracle,或者是Sqlite、Access、MySql等等,都一样可以很好的生成所需的开发代码的。
工具生成了界面布局代码,以及界面后台逻辑代码,这样的代码正是我们开发所需要的,我们看到生成后的界面代码(没有修改代码的),在VS里面的真实效果如下。
上面的布局采用了LayoutControl来进行布局控制,这是一种很好的布局控制方法,它除了使得界面更加美观外,还能非常*调整每个控件的位置及大小。
当然,我们一般为了美观需要,会对界面进行一定的调整,由于DevExpress控件类型变化切换很方便,所以这种调整很*高效,调整后的界面如下所示。
比起十几秒钟弄好一个界面,纯手工做这样的界面,没有十几分钟,估计弄不好的,而且容易出错,最重要的问题,就是团队开发的时候,这个统一性就很有保证,开发效率高,带来Bug也会很少。
3、基于传统的Winform界面快速生成
传统的Winform界面和DotNetBar样式的界面生成,和上面的DevExpress样式代码很类似,不过控件不同而已,由于不同的需要,用传统界面元素开发,也是一种常见的开发模式,因此我的代码生成工具也支持这种常规的界面生成,来辅助大家做好界面的工作。
除了设置以上界面样式外,其他生成操作一样。得到的界面效果如下所示。
和DevExpress控件界面代码类似,这里也使用了TableLayout的布局控件,用来较好控制布局的高度宽度,以及每行位置等,这样整体效果就很好,也容易进行界面元素的控制。