在Model-Driven App中使用自定义页面(Custom Page)

我是微软Dynamics 365 & Power Platform方面的工程师/顾问罗勇,也是2015年7月到2018年6月连续三年Dynamics CRM/Business Solutions方面的微软最有价值专家(Microsoft MVP),这是我的第478篇原创文章,写于2022年8月24日。

这个文章不是以前我写的博文 ​​嵌入Canvas App到Model-Driven App中​​ 那种,而且以前嵌入的这种也不再推荐使用了

今天要介绍的内容请参考官方文档:

  • ​​Overview of custom pages for model-driven apps​​
  • ​​Add a custom page to your model-driven app​​
  • ​​Design a custom page for your model-driven app​​
  • ​​Navigating to a custom page using client API​​
  • ​​Use Power Fx in a custom page for your model-driven app​​
  • ​​Add canvas components to a custom page for your model-driven app​​
  • ​​Add code components to a custom page for your model-driven app​​
  • ​​Known issues with custom pages in a model-driven app​​
  • ​​Use Monitor to troubleshoot custom page behavior in a model-driven app​​

为了说明,我假想个场景,就是在一个实体的表单上增加一个按钮,点击打开一个custom page,这个page展示文件字段的图片(假设上传的文件是图片)。

添加Custom Page的方法有多种,我使用常见的这种,登录 ​​https://make.powerapps.com/​​ ,打开自己建立的解决方案,点击 New > App > Page.

打开的界面如下,这个和Canvas App的开发界面非常相似,就是个简版的Power Apps Studio。从官方文档也可以知道,目前只支持独立Canvas App程序支持的部分控件。

在Model-Driven App中使用自定义页面(Custom Page)

我这里插入一个Media分组下的 Image控件,将其 X, Y属性都设置为0, Width设置为Parent.Width, Height 设置为Parent.Height 。

在Model-Driven App中使用自定义页面(Custom Page)

然后点击左侧的 Data图标,添加数据源,点击Add data将用到的表添加进来。

在Model-Driven App中使用自定义页面(Custom Page)

我这里设置 App对象 的OnStart 事件代码如下:

Set(
RecordItem,
If(
IsBlank(Param("recordId")),
First('Test Entities'),
LookUp(
'Test Entities',
'Test Entity' = GUID(Param("recordId"))
)
)
)

在Model-Driven App中使用自定义页面(Custom Page)

然后我将前面插入到屏幕中的Image的Image属性设置为"​https://org51fb1eac.crm5.dynamics.com/api/data/v9.2/ly_testentities​​(" & Text(RecordItem.'Test Entity') & ")/ly_file/$value" 。可以看到我这个url的前面部分是写死的,可以将这个作为环境变量存储起来,这样就灵活些,如何做请参考我的博文 ​​Canvas App中获取存储格式为JSON的环境变量的值并解析成集合​​ ,我这里为了简化就不做这么复杂了。

在Model-Driven App中使用自定义页面(Custom Page)

点击Save按钮,输入个好名字,然后保存。

在Model-Driven App中使用自定义页面(Custom Page)

最好发布下:

在Model-Driven App中使用自定义页面(Custom Page)

然后在解决方案中就会新增一条Type为Page的记录,复制好Name,后面代码要用。

在Model-Driven App中使用自定义页面(Custom Page)

当前的这个Model-Driven App要能使用的话还需要添加进来,编辑这个App,点击 Add page.

在Model-Driven App中使用自定义页面(Custom Page)

选择 Custom 后点击 Next 按钮。

在Model-Driven App中使用自定义页面(Custom Page)

选择 Use an existing custom page,然后选择要添加的custom page,因为这个page我不需要显示在导航栏,所以取消掉 Show in navigation 这个前面的复选框,然后点击 Add 按钮。

在Model-Driven App中使用自定义页面(Custom Page)

然后我还需要保存并发布这个App。以后若是修改了Custom Page,除了这个Custom Page要发布外,用到这个Custom Page的Model-driven App也要发布。

在Model-Driven App中使用自定义页面(Custom Page)

为了测试效果,我在表单界面新增一个查看图片的按钮。

在Model-Driven App中使用自定义页面(Custom Page)

执行的代码如下:注意代码传递recordId的时候要去掉前后的 { 和 }字符,否则custom page接收到的这个参数的值为空。

"use strict";
var LuoYong = window.LuoYong || {};
LuoYong.TestEntity = LuoYong.TestEntity || {};
(function () {

this.ShowCustomPageAction = function (primaryControl) {
try {
var formContext = primaryControl;
var pageInput = {
pageType: "custom",
name: "ly_luoyongdemocustompageapp_b9378",
entityName: "ly_testentity",
recordId: formContext.data.entity.getId().replace('{', '').replace('}', ''),
};
var navigationOptions = {
target: 2,
position: 1,
width: { value: 50, unit: "%" },
title: "查看图片"
};
Xrm.Navigation.navigateTo(pageInput, navigationOptions)
.then(
function () {
// Called when page opens
}
).catch(
function (error) {
// Handle error
}
);
}
catch (ex) {
Xrm.Navigation.openErrorDialog({ message: ex.message });
}
};
}).call(LuoYong.TestEntity);

点击后看到的效果如下:

在Model-Driven App中使用自定义页面(Custom Page)