我正在开发 SAPUI5 应用程序。我有一个 XML 视图,其中包含一个 XML Fragment 和一个要保存的按钮。
该片段包含一些控件,例如下拉列表、文本字段和表格。 当我按下保存按钮时,我需要获取表中的所有行并调用 OData 更新服务。
问题出在视图控制器中的
onSave
方法中。使用表 ID 访问表时出现错误。谁能帮助我并建议我如何通过控制器中的 ID 访问片段中使用的控件?
这是代码片段:
查看:
<mvc:View xmlns:mvc="sap.ui.core.mvc" xmlns:core="sap.ui.core" xmlns:form="sap.ui.layout.form" xmlns="sap.m">
<Page>
...
<form:SimpleForm>
<core:Fragment id ="fr1" fragmentName="first" type="XML" />
<Button id="id1" press="onSave" />
</form:SimpleForm>
</Page>
</mvc:View>
片段定义:
<core:FragmentDefinition xmlns="sap.m" xmlns:core="sap.ui.core">
<Table id="tab1" mode="MultiSelect">
...
</Table>
</core:FragmentDefinition>
控制器:
sap.ui.controller("view", {
onSave: function() {
//var tab = this.getView().byId("tab1"); // Not working
var tab = sap.ui.getCore().byId("tab1"); // Not working
},
// ...
});
访问片段内的控件取决于片段的创建方式。以下是场景列表,其中包含用于获取控件引用的相应 API。
给出:
this
作为当前控制器实例的引用Fragment
需要 sap/ui/core/Fragment
<MyControl id="controlId"/>
在片段定义中this.byId("controlId");
...如果片段是使用视图 ID(推荐)直接或间接创建的:
this.loadFragment({ name: "..." }); // id: view ID given by default, API since 1.93
<!-- In the view embedding the fragment declaratively: -->
<core:Fragment fragmentName="..." type="XML"/><!-- id = view ID given by default -->
Fragment.load({ // API since 1.58
id: this.getView().getId(),
name: "...",
controller: this,
});
sap.ui.xmlfragment(this.getView().getId(), "...", this); // Deprecated
生成的全局 ID:
"componentId---viewId--controlId"
*
this.byId(Fragment.createId("fragmentId", "controlId"));
...如果给定片段 ID 与视图 ID 组合:
this.loadFragment({ id: this.createId("fragmentId"), name: "..." });
<core:Fragment id="fragmentId" fragmentName="..." type="XML"/>
Fragment.load({
id: this.createId("fragmentId"),
name: "...",
controller: this,
});
sap.ui.xmlfragment(this.createId("fragmentId"), "...", this); // Deprecated
生成的全局 ID:
"componentId---viewId--fragmentId--controlId"
*
Fragment.byId("fragmentId", "controlId");
...如果只给出了片段 ID 而没有与视图 ID 相结合:
this.loadFragment({
id: "fragmentId",
name: "...",
autoPrefixId: false, // Explicitly disabled view ID as prefix
});
Fragment.load({
id: "fragmentId",
name: "...",
controller: this,
});
sap.ui.xmlfragment("fragmentId", "...", this); // Deprecated
生成的全局 ID:
"fragmentId--controlId"
*
Element.getElementById("controlId") // since 1.119
Element.registry.get("controlId") // since 1.67
(原
sap.ui.getCore().byId("controlId")
)
...如果没有给出前缀 ID。 不推荐以下设置,因为片段定义中的所有控件 ID 将在没有任何前缀的情况下全局注册。无法保证 ID 的唯一性!
this.loadFragment({ name: "...", autoPrefixId: false }); // Not recommended if no id
Fragment.load({ name: "...", controller: this }); // Not recommended
sap.ui.xmlfragment("demo.view.MyFragment", this); // Deprecated
生成的全局 ID:
"controlId"
* 不要依赖生成的全局 ID,例如,在应用程序中手动连接 ID 部分。始终使用上面提到的专用 API,例如
byId
和 createId
。请参阅稳定 ID:您需要了解的一切。
byId
不要直接访问片段控件,而是考虑通过数据绑定操作 UI。模型中的更改将自动反映在 UI 中,并且,如果启用双向绑定,来自 UI 的用户输入将直接存储在模型中。
开发 Fiori 元素扩展时,请确保遵守记录的 兼容性指南,尤其是关于
byId
:
[...] 不要访问或操纵 SAP Fiori 元素的内部编码。
[...] 不得访问任何未在您的视图扩展中定义的 UI 元素。⚠注意
如果您不遵守此指南,您的应用程序可能无法与未来的 SAPUI5 版本一起使用,因为 SAP Fiori 元素可能会将控件交换为具有不同 API 的新元素。
查看 GitHub 上的 OpenUI5 代码,如果
<Fragment/>
本身没有 具有显式 ID,则 Fragment 似乎会将本地 ID 生成委托给包含视图。
因此,一旦您从 this.getView().byId("tab1")
元素中删除
id="fr1"
属性,您的代码
<Fragment/>
就应该可以正常工作。使用显式 ID 时,有一个
static Fragment.byId
// Fragment required from "sap/ui/core/Fragment"
var fragmentId = this.getView().createId("fr1");
var tab = Fragment.byId(fragmentId, "tab1");
var prefix = this.getView().createId("").replace("--", "");
var fragment = sap.ui.xmlfragment(prefix, "-- XML fragment name --", this);
在此之后,您可以像使用任何其他控件一样使用 this.getView().byId("tab1") 。