Lightswitch: 使用视图

分享于 

12分钟阅读

Web开发

  繁體

介绍

在本文中,我将讨论如何有一个浏览屏幕来自一个表,以及如何从视图中获得一个编辑屏幕。 因此,在保存数据时会出现下一个问题,保存工作流是如何工作的? 如果你知道lightswitch是如何工作的,那么你肯定会理解我在这里试图解决的。 对于那些不知道的人,编辑和保存工作流在我们创建浏览屏幕的表上工作。 但是在我们的例子中,如何使这个场景工作。

背景

我的技术明智,我不想在这里详细解释。 你可以一次浏览lightswitch的基础知识。 这很简单。因为这是一篇高级文章,我会直接跳转到问题语句。

我使用 Visual Studio Lightswitch 2013项目并使用 SQL Server 管理 Studio 2013. 我有一个名为 tblFamily的表,它的create 语句将如下所示:

CREATETABLE [dbo].[tblFamily](
 [FamilyID] [int] IDENTITY(1,1) NOTFORREPLICATIONNOTNULL,
 [FamilyTypeID] [int] NOTNULL,
 [Name] [varchar](100) NOTNULL,
 [OffsetFromMaxAsAtDate] [tinyint] NULLDEFAULT ((1)),
 [TimeDataExpires] [time](7) NULL,
 [ExcludeZeroNumberOfUnits] [bit] NOTNULLDEFAULT ((1)),
 [PrefilterConstituents] [bit] NULLDEFAULT ((0)),
 [LimitEndDate] [bit] NOTNULLDEFAULT ((0)),
 [IgnoreForPricing] [bit] NOTNULLDEFAULT ((0)),
 [AutoAddOddLots] [bit] NULLDEFAULT ((0)),[AutoAddMissingListing] [bit] NOTNULLDEFAULT ((0)),
 CONSTRAINT [PK_tblFamily] PRIMARYKEYCLUSTERED ( [FamilyID] ASC)
) ON [PRIMARY]

有了这个表格,我就会创建我的浏览屏幕。 主要点是 TimeDataExpires 属性,它是 datatype time

若要创建视图,我将执行以下操作。 在本文后面我将解释为什么创建这个视图以及它的目的是什么。 在这个视图中,我将 TimeDataExpires 转换为 string datatype

CREATEview [dbo].[vwFamilyProcessData]asselect FamilyID,
OffsetFromMaxAsAtDate as OffsetFromMaxAsAtDate,
ExcludeZeroNumberOfUnits as ExcludeZeroNumberOfUnits,
PrefilterConstituents as PrefilterConstituents,
LimitEndDate as LimitEndDate,
IgnoreForPricing as IgnoreForPricing,
AutoAddMissingListing as AutoAddMissingListing,
AutoAddOddLots as AutoAddOddLots,
cast(TimeDataExpires asvarchar(20)) as TimeDataExpiresfrom tblFamily

使用代码

创建新的lightswitch 项目。 创建一个屏幕数据为 tblFamilies ( 所有实体将显示为复数- Entity Framework 概念)的浏览屏幕。 也创建一个按钮来编辑这里数据。 因此,选择 tblFamilies.editSelected 并导航到一个新屏幕,然后单击 ok"。 你的屏幕布局应该与下面的屏幕。 请忽略隐藏的按钮,我稍后解释。 现在运行项目。

现在点击 Edittbl 家族按钮。 并尝试编辑时间数据过期字段。 试图编辑这里字段时,它将自动关闭编辑屏幕。 无论如何,你将无法编辑这里屏幕。 你还可以尝试在浏览屏幕上查看这里数据,方法如下所示:

这里外,如果在浏览器中运行这里屏幕,则会注意到没有数据在时间数据过期属性中呈现。

因此,为了解决这个问题,我们将使用视图在屏幕上呈现这个属性。 现在创建一个添加/编辑详细信息屏幕,用屏幕数据作为 vwFamilyProcessData,然后单击确定。 将创建一个带有编辑对话框的屏幕,如下所示:

注意 : 请忽略额外的字段。 他们是我的view。

现在回到浏览家庭屏幕并添加如下所示的按钮。 创建按钮时,不要选择任何现有方法。 选择Write我自己的方法和方法 NAME 作为 SaveFamilyProcessData

右键单击保存族进程数据按钮。 在编辑执行代码中选择。 添加以下代码行:

myapp.BrowseFamily.SaveFamilyProcessData_execute = function (screen) {
myapp.showEditvwFamilyProcessData(screen.vwFamilyProcessData, { 
 afterClosed: function (addEditScreen, navigationAction) {
 if (navigationAction === msls.NavigateBackAction.commit) {
 screen.tblFamilies.refresh();
 }
 }
 });
};

myapp.BrowseFamily.SaveFamilyProcessData_execute 我们可以指定点击 SaveFamilyProcessData 按钮时可以采取什么操作。

myapp.showEditvwFamilyProcessData() 指定在单击 SaveFamilyProcessData 按钮时打开 EditvwFamilyProcessData 屏幕。 因为它指定了需要在屏幕上显示什么数据,所以我们将 screen.vwFamilyProcessData 作为第一个参数传递。 如果你没有传递任何东西,那么它会打开 EditvwFamilyProcessData 屏幕。 最幸运的是,roo会想出选择哪个 FamilyID,在编辑屏幕上显示该数据。 我们不需要考虑那部分。

我们已经添加了 afterClosed 处理程序来在成功保存操作后刷新屏幕。 我们需要手动添加这段代码,因为在保存操作之后,基本屏幕不会被刷新。

现在主要的问题是。 如何从视图中保存数据。 因为我已经为你解决了这个问题,所以现在看起来很容易。 但相信我花了超过 2周的时间来解决这个问题。

转到服务器项目,双击数据源下的vwFamilyProcessData.Isml 文件。

现在去写代码并选择更新方法。 请参考下面的屏幕:

添加这一段代码:

partial void vwFamilyProcessDatas_Updating(vwFamilyProcessData entity)
 {
 if(entity.Details.EntityState.ToString() == "Modified")
 {
 var AutoAddMissingListing = entity.AutoAddMissingListing;
 var AutoAddOddLots = entity.AutoAddOddLots;
 var DefaultFilterValue = entity.DefaultFilterValue;
 var ExcludeZeroNumberOfUnits = entity.ExcludeZeroNumberOfUnits;
 var IgnoreForPricing = entity.IgnoreForPricing;
 var LimitEndDate = entity.LimitEndDate;
 var OffsetFromMaxAsAtDate = entity.OffsetFromMaxAsAtDate;
 var PrefilterConstituents = entity.PrefilterConstituents;
 var TimeDataExpires = entity.TimeDataExpires;
 tblFamily objFamily = tblFamilies.Where(f => f.FamilyID == entity.FamilyID).Single();
 objFamily.AutoAddMissingListing = AutoAddMissingListing;
 objFamily.AutoAddOddLots = AutoAddOddLots;
 objFamily.DefaultFilterValue = DefaultFilterValue;
 objFamily.ExcludeZeroNumberOfUnits = ExcludeZeroNumberOfUnits;
 objFamily.IgnoreForPricing = IgnoreForPricing;
 objFamily.LimitEndDate = LimitEndDate;
 objFamily.OffsetFromMaxAsAtDate = OffsetFromMaxAsAtDate;
 objFamily.PrefilterConstituents = PrefilterConstituents;
 objFamily.TimeDataExpires = TimeSpan.Parse(TimeDataExpires);
 entity.Details.DiscardChanges();
 }
}

我将试着解释。 lightswitch遵循保存流水线流程。 它遵循一组特定规则并始终遵循相同的管道。 保存管道是自动生成的每个LightSwitch应用程序。 因此,理解这个概念是非常重要的。

要了解有关这个概念的详细信息,请浏览本文的

Lightswitch按照你在屏幕上看到的顺序调用编写代码部分中列出的常规方法。 另外,由于我们试图在屏幕上编辑填充的数据,所以使用 Updating 方法更有意义。

每当添加/编辑屏幕中的更改都由调用时,就会调用该方法。 所以当我们打开屏幕 EditvwFamilyProcessData 并尝试编辑这个屏幕上的数据时,lightswitch捕获这个更改,并将更改后的数据包含到save管道。

所以 vwFamilyProcessData 类型的实体捕获屏幕上的所有数据。 使用这一行代码,如果 entity.Details.EntityState.ToString() =="Modified" 检查实体是否已经修改或者未被修改。 如果 EntityStateModified,那么它就会进入 if 循环。 我们将屏幕上的所有数据捕获到本地变量中。 然后使用编辑和存储的FamilyID 载入族细节,并将值存储在 tblFamily 对象中,例如。

现在这个棘手的部分。 注意我确实放弃了对实体的更改。 因为lightswitch理解了 TimeDataExpires 属性,因此我必须将它的理解为计算属性或者派生属性。 请参考下面的图片:

同样,如果你认为。 在视图中,TimeDataExpires 是一个 string 数据类型,在 tblFamily 中是实际表,它是一个 Time 数据类型。 由于存在数据类型不匹配,所以lightswitch显然不允许保存数据。 如果没有数据类型不匹配,lightswitch将成功保存这里数据。

因此我们必须放弃对 vwFamilyProcessData的实体更改并保存对 tblFamily 所做的实体更改。 Lightswitch将捕获 tblFamily 所做的一些更改,并在保存管道中处理这些信息。 因此,数据将直接保存到 tblFamily 表中,用于特定的FamilyID

在浏览器上保存全部并运行项目。 选择一个族并尝试通过单击保存族进程数据按钮来编辑它。 将显示 EditvwFamilyProcessData 屏幕,其中包含所选 FamilyID的数据。 尝试编辑屏幕上的任何数据,并单击顶部的保存按钮。 成功保存操作后,编辑屏幕将关闭,因这里屏幕将在 afterClosed 处理程序中添加代码。

非常重要的笔记: 不要删除我们首先创建的按钮 Edittbl 族按钮。 这里按钮用于将数据绑定到浏览族屏幕的页面加载上。 如果你删除了这个按钮,那么当你第一次尝试点击保存族过程数据按钮时,它会给你一个空白的。 关闭弹出窗口后,如果再次单击SaveFamilyProcessData按钮并尝试第二次打开弹出屏幕,它将成功加载数据。 因此,为了避免这个问题,不要删除Edittbl族按钮,而是通过清除按钮的IsVisible属性使它的不可见。 请参考下面的图:


相关文章