Entity Framework4.0 (八) EF4的数据绑定(转 )

前面我们介绍了EF4对数据的增删改查的操作。可以借助于EF4,开发人员的工作量将变得特别简单。

这次我们介绍EF4的数据绑定功能。这次你将会发现EF4的更加简单方面的又一用途:即EF4作为数据源控件的“数据源”。

汗!!好拗口哟。为什么这么说呢?

因为当我们在项目中使用数据源控件时,是需要指出给该数据源控件从哪里取数据的,即指出数据源控件的数据源。以 前我们会用Dataset作为数据源控件的数据源。然后,由Dataadapter与数据库交互,把数据填充到Dataset中。再呈现到显示控件上(如 datagridview)。这次我们使用EF4的来代替以前Dataadapter与dataset所一起完成的任务。我们已经知道:EF4是可以把数 据表的记录映射成实体与实体集合,并且可跟踪管理这些实体。那么我们就可以把这些实体和实体集合作为数据源控件的数据源。这样数据源控件不需要直接和数据 库打交道,而是和EF4的实体容器(Container)交互,再由EF4和数据库交互。

======================================================

好了,我们先启动VS2010.

1. File->new-->Windows form project。(名字:EFDataBindingDemo)

2. 在解决方案上,右键--》添加--》新项目--》类库。(名称:EFData)。(我们为体现分层的思想,这次把*.EDMX文件单独建立到一个类库项目中。),

3. 在EFData类库项目上面右键--》添加--》ADO.Net entity data model 。(名称:Northwind)。点击“确定”,如下图:

4.找到服务器上的northwind数据库。如下图:

5.选择三张表:Category,Product,Supplier。如下图:

6.在EFDataBindingDemo项目中添加项目引用:如下图:(同时别忘了把EFData项目中的App.config文件也烤贝到 EFDataBindingDemo的项目下面。最简单的方法是你可以直接用鼠标把该文件拖拽到EFDataBindingDemo的项目中)

7.添加.NET类库引用,如下图:

8. 选中EFDataBindingDemo项目,然后打开数据源窗口,如下图:

9.点击数据源窗口上,最左边的的按钮--》添加数据源:如现数据源类型供选择,如下图:

10.点击Next,如下图:如果出现空白,说明你的*.EDMX忘记了编译,

选择“取消”。编译EFData项目,然后重新添加数据源,到这一步。

注意:当你用鼠标选中“EFData”项目时,数据源窗口显示的是“EFData”项目的数据源;只有你选中EFDataBindingDemo项目时,数据源窗口显示的才是EFDataBindingDemo项目的数据源。不要混淆了。

11.重新选中EFDataBindingDemo项目,在数据源窗口--》添加数据源,重复步骤9,如下图:

12.此时数据源窗口会显示添加过的数据源:如下图:

13.拖拽“product”数据源节点,到form1上面,松开鼠标。如下图:(注意观察图中5个标号,这是自动添加)

 

14.运行程序:如下图:

说明:没有取到数据,很失望吧?呵呵,之前我们用指向dataset的数据源绑定控件时,是主动从数据库往外 取,所以是可以加载到数据的。但是现在我们不是直接使用数据库,而是使用EF4(其实就是使用EF4的容器),再有EF4与数据库打交道。因为,我们的所 有实体都是放到context容器中的,而现在我们并没有创建这个容器啊,所以加载不到数据(实体)。

15.我们在窗体的Load事件中添加下面的代码:

private void Form1_Load(object sender, EventArgs e)
         {
             var context = new NorthwindEntities();
             ObjectResult<Product> products = context.Products.Execute(MergeOption.AppendOnly);
             // 给数据源控件的数据源属性赋值。
             this.productBindingSource.DataSource = products;
         }

运行程序,如下图:(数据是加载了,但是Category,和Supplier两列的数据只有类型,没有实际数据值)

16.在productDataGridView上面右键——》edit columns;添加两列CategoryName和SupplierContactNameName,如下图:(每列的Name和HeaderText 设置相同)把新添加的列移到最下端,方便查看。

在productDataGridView控件的RowPrePaint事件中添加如下代码:

 1 private void productDataGridView_RowPrePaint(object sender, DataGridViewRowPrePaintEventArgs e)
 2          {
 3              if (e.RowIndex < productBindingSource.Count)
 4              {
 5                  var prod = (Product)productBindingSource[e.RowIndex];
 6  
 7                  var grid = productDataGridView;
 8                  if (prod.Category != null)
 9                  {
10                      grid.Rows[e.RowIndex].Cells[CategoryName.Index].Value = prod.Category.CategoryName;
11                  }
12  
13                  if (prod.Supplier != null)
14                  {
15                      grid.Rows[e.RowIndex].Cells[SupplierContactName.Index].Value = prod.Supplier.CompanyName;
16                  }
17              }
18          }

17.运行代码:如下图:(图中的两个红框分别是:处理前的列和处理后的列)

18. 使用添加、删除、保存功能:

productDataGridView控件的右上方有一个黑色的小小实心三角形,叫“智能标记”。点开智能标记,设置里面的Enable Adding,Enable Editing, Enable Deleting,为选中状态。

窗体上方的导航条,有三个图标:添加,删除,保存。分别用鼠标右键-》Enable 。把它们选为可用。分别为这三个图标添加click事件(在上面双击,即可)

我们把窗体load事件中定义的context移到类中,这样多个方法都可以使用这个context变量。

添加,删除按钮是直接对productBindingSource进行了修改。而productBindingSource会直接影响productDataGridView的变化。这些我们都不必处理。

下面我们处理保存按钮事件:代码如下:

 1 private void productBindingNavigatorSaveItem_Click(object sender, EventArgs e)
 2          {
 3         
 4                  try
 5                  {
 6                      this.productBindingSource.EndEdit();              
 7                      context.SaveChanges();
 8                      MessageBox.Show("save successfuly");
 9                  }
10                  catch (Exception ex)
11                  {
12                      if (ex.InnerException != null)
13                          MessageBox.Show(ex.InnerException.Message.ToString());
14                      else
15                          MessageBox.Show(ex.Message.ToString());
16                  }
17           
18          }
运行程序,这时你可以进行添加、修改和删除,然后保存到数据库中。

注意:

1.在删除Product时,可能会引发异常,因为数据库中有Order_detail表的外键引用了product中的主键。所以,你只能删除那些没有被其它表引用到的product。

2.一般情况下,在界面显示时,我们是不让用看到ID号的,因为这些对用户来说没有意义,所以我们在实际项目中最好把这一ID列(无论是主键列还是外键列)全部隐藏掉。看清是隐藏掉,不是删除掉,因为我们在程序中是要使用这些ID号进行CRUD的操作的。

3. 在处理更新的某一个单元格的数据的时候。我遇到了困惑:以前使用dataset作数据绑定时,是直接可以把对单元格的修改反馈到数据库中的,而这次我使用 EF时,却不能把对单元格的修改反馈到数据库了,即使我调用了context.savechanges()方法。后来我找了许多资料,也没能解决问题。在 我一次偶然的测试中,我一次性修改了多个单元格,然后保存。这次竟然保存成功了。感觉是因为我对单元格作的修改量太小了,context并没有把它们及时 更新入数据库中,而是对这些进行了本地缓存的原因。但我只是猜测,并不确定。希望高人给我指点一下。、谢谢。)

可以看到,我们可以非常轻松地处理这些数据了。是不是感觉世界又美好了许多。哈哈。

窗体后台完整代码如下:

窗体后台完整代码
 1    public partial class Form1 : Form
 2      {
 3          NorthwindEntities context;
 4  
 5          public Form1()
 6          {
 7              InitializeComponent();
 8          }
 9  
10          private void Form1_Load(object sender, EventArgs e)
11          {
12              context = new NorthwindEntities();
13              ObjectResult<Product> products = context.Products.Execute(MergeOption.OverwriteChanges);
14              // 给数据源控件的数据源属性赋值。
15              this.productBindingSource.DataSource = products;
16            
17          }
18  
19          private void productDataGridView_RowPrePaint(object sender, DataGridViewRowPrePaintEventArgs e)
20          {
21              if (e.RowIndex < productBindingSource.Count)
22              {
23                  var prod = (Product)productBindingSource[e.RowIndex];
24  
25                  var grid = productDataGridView;
26                  if (prod.Category != null)
27                  {
28                      grid.Rows[e.RowIndex].Cells[CategoryName.Index].Value = prod.Category.CategoryName;
29                  }
30  
31                  if (prod.Supplier != null)
32                  {
33                      grid.Rows[e.RowIndex].Cells[SupplierContactName.Index].Value = prod.Supplier.CompanyName;
34                  }
35              }
36          }
37  
38  
39  
40          private void productBindingNavigatorSaveItem_Click(object sender, EventArgs e)
41          {
42         
43                  try
44                  {
45                      this.productBindingSource.EndEdit();              
46                      context.SaveChanges();
47                      MessageBox.Show("save successfuly");
48                  }
49                  catch (Exception ex)
50                  {
51                      if (ex.InnerException != null)
52                          MessageBox.Show(ex.InnerException.Message.ToString());
53                      else
54                          MessageBox.Show(ex.Message.ToString());
55                  }
56           
57          }
58  
59               
60      }

转载于:https://www.cnblogs.com/tonykan/archive/2012/11/22/2781855.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值