Javascript 通过控制器动态创建UI元素,并将它们绑定到模型中的特定属性

Javascript 通过控制器动态创建UI元素,并将它们绑定到模型中的特定属性,javascript,data-binding,sapui5,sap-fiori,two-way-binding,Javascript,Data Binding,Sapui5,Sap Fiori,Two Way Binding,我一直在尝试根据JSONmodel中的特定对象(一个对象数组)向对话框中添加动态内容 我的模型具有以下结构,我将其设置为(虚拟数据): 注意:我有多个模型在此控制器视图中处于活动状态,每个模型都有自己的模型数据 因此,我已成功设置了模型数据,现在我可以通过以下方式访问它: var modelData= this.oView.getModel("myModel").oData; 我现在想要的是动态创建sap.m.Dialog并用多个sap.m.Input元素动态填充它,这些元素的值基于我的模型中

我一直在尝试根据JSONmodel中的特定对象(一个对象数组)向对话框中添加动态内容

我的模型具有以下结构,我将其设置为(虚拟数据):

注意:我有多个模型在此控制器视图中处于活动状态,每个模型都有自己的模型数据

因此,我已成功设置了模型数据,现在我可以通过以下方式访问它:

var modelData= this.oView.getModel("myModel").oData;
我现在想要的是动态创建
sap.m.Dialog
并用多个
sap.m.Input
元素动态填充它,这些元素的值基于我的模型中的单个对象:

var getDialogContent = function(modelData){         
            var arr = [];
            var keys = Object.keys(modelData[0]); // property names. I hard-coded first obj for test.
            // I want to use these properties and bind a new input on dialog for each property.

            jQuery.each(keys, function(i, key) {

// 'myModel>/emp/0/'+key is a supposed full path to property...
//  according to this link: 
//  https://sapui5.hana.ondemand.com/1.36.6/docs/guide/91f0ed206f4d1014b6dd926db0e91070.html

                    newInput.bindProperty("value", 'myModel>/emp/0/' + key); //key is col1 the first time
                    newInput.setProperty("description", key);
                    newInput.setProperty("type", sap.m.InputType.Number);
                    arr.push(newInput); 
            });
            return arr;
        };
我在对话框的content属性中调用getDialogContent()来设置其内容

现在,除了绑定
newInput.bindProperty(“value”,'myModel>/emp/0/'+键)之外,一切都正常了,显示的输入字段只是空的,没有显示绑定的迹象,同样
newInput.getBindingContext(“myModel”)返回未定义的

        var dialog = new sap.m.Dialog({
            title: 'Dynamic dialog: ',
            type: 'Message',
            content: getDialogContent(modelData),
            buttons: new sap.m.Button({
                text: 'Cancel',
                press: function () {                    
                    dialog.close();
                }
            }),
            afterClose: function() {
                dialog.destroy();
            }
        });                    
有人知道这里出了什么问题吗?为什么我不能将我的属性绑定到输入元素?我基本上只想将动态输入字段的值绑定到JSON模型中对象数组中的任意对象。欢迎提出任何建议

编辑(解决方案):
在var
keys=Object.keys(modelData[0])上行I将
modelData[0]
替换为
modelData[“emp”][0]
。现在它可以工作了。

你呢?当我在我们的应用程序中删除该步骤时,结果与您描述的完全一样:字段为空,并且
getBindingContext()
返回
未定义的

以可重用方式实现对话框的最佳方法之一是中描述的方法。为了检索在该视图上设置的模型,您必须将对话框作为依赖项添加到“父”视图

onDialogOpen: function () {
            if (!this.oDialog) {
                this.oDialog =  new sap.m.Dialog({
                   title: 'Dynamic dialog: ',
                   type: 'Message',
                   content: getDialogContent(modelData),
                   buttons: new sap.m.Button({
                      text: 'Cancel',
                      press: function () {                    
                        this.oDialog.close();
                      }.bind(this)
                   }),
                   afterClose: function() {
                     this.oDialog.destroy();
                   }.bind(this)
               });            
               //to get access to the view models
               this.getView().addDependent(this.oDialog);
            }    
            this.oDialog.open();
        },

嗨,约翰。你确定你说的是对话而不是片段吗?因为我还没有看到向视图的依赖项添加对话框的示例。但在你的链接中,让我感兴趣的是这样一句话:“对话框是特殊的,因为它们在常规应用程序内容之上打开,因此不属于特定的视图。”这是否意味着对话框无法访问视图的绑定上下文?我现在不能回答这个问题,因为我在家。。我明天上班时再回来看看。:)嘿,约翰,我把它弄到手了。我将这一行:var keys=Object.keys(modelData[0])改为:var keys=Object.keys(modelData[“emp”][0]),并像以前一样使用路径:newInput.bindProperty(“value”,“troskoviModel>/emp/0/”+key)昨天我尝试了一百万种变体,但我想我错过了这一种。起初,我在模型对象中直接添加数据,但没有“emp”标识符,因此无法工作。所以我添加了“'myModel>/emp/0/'+key”,这样我就可以像文档中建议的那样使用绝对路径。但我猜modelData[“emp”][0]是缺少的。感谢我从未向依赖项添加对话框的方式,我只是像其他任何输入元素一样动态创建了它。哦,天哪,我刚刚意识到“您是否将对话框添加到视图的依赖项中?”实际上是指这个。getView().addDependent(dialog)…嘿,我对此进行了一点修改,从我收集的信息来看,您的代码示例与我的不同之处在于
.bind(this)
after
afterClose
事件属性。
.bind(this)
实际上做什么?我在回复约翰的评论时解释说,不管怎样,我还是成功了。我还在输入字段上添加了一个更改事件:
var newInput=new sap.m.input({change:this.onInputChanged})
,但我无法将任何参数传递给onInputChanged函数,因为当我在括号内添加一个参数时,
this.onInputChanged(arg)
,会立即调用func。知道通过ARG的正确方法是什么吗?谢谢我的代码与您的代码不同,还因为我添加了两行基本代码(1)//以访问视图模型(2)this.getView().addDependent(this.oDialog);您要问的是一个基本的javascript问题。。。。这就是.bind()被发明的原因。我相信你可以用谷歌搜索它,找到大量关于它的信息。对不起,我刚刚意识到我没有发布所有的控制器代码。但是我已经添加了
this.getView().addDependent(this.oDialog)
。我对此没有异议。还有,很抱歉这个愚蠢的问题,我一时疏忽,忘记了bind()是一个纯js:)我想问的是,您可能知道如何将自定义参数传递给
newInput=new sap.m.Input({change:this.onInputChanged})
的更改事件吗?现在,我的onInputChanged func只接受作为触发事件的对象自动传递的参数。我也想传递“this”。没关系,我从你的书中拿出一页,在
sap.m.Input({change:this.onInputChanged})中添加了.bind(this)到
this.onInputChanged
。谢谢
onDialogOpen: function () {
            if (!this.oDialog) {
                this.oDialog =  new sap.m.Dialog({
                   title: 'Dynamic dialog: ',
                   type: 'Message',
                   content: getDialogContent(modelData),
                   buttons: new sap.m.Button({
                      text: 'Cancel',
                      press: function () {                    
                        this.oDialog.close();
                      }.bind(this)
                   }),
                   afterClose: function() {
                     this.oDialog.destroy();
                   }.bind(this)
               });            
               //to get access to the view models
               this.getView().addDependent(this.oDialog);
            }    
            this.oDialog.open();
        },