在数据加载角指令模板更新 [英] Angular Directive Template Update on Data Load
问题描述
我有一个指令正在通过API调用接收其数据。该指令本身工作正常,问题出现的(我相信)的,因为指令API调用完成之前加载。这导致整个事情只是不工作。不是我期望的输出,我只是得到 {{}用户}
。
I have a directive whose data is being received via an api call. The directive itself works fine, the problem arises (I believe) because the directive is loaded before the api call finishes. This results in the whole shebang just not working. Instead of my expected output, I just get {{user}}
.
我的指令是这样的:
app.directive('myDirective', function() {
return {
restrict: 'A',
require: '^ngModel',
scope: {
ngModel: '=',
},
template: '<tbody style="background-color: red;" ng-bind-html="renderHtml(listing_html)"></tbody>',
controller: ['$scope', '$http', '$sce',
function($scope, $http, $sce) {
$scope.listing_html += "<td>{{user.name}}</td>"
$scope.renderHtml = function(html_code) {
return $sce.trustAsHtml(html_code);
};
}
],
link: function(scope, iElement, iAttrs, ctrl) {
scope.$watch('ngModel', function(newVal) {
// This *is* firing after the data arrives, but even then the
// {{user}} object is populated. And the `user in ngModel` doesn't
// run correctly either.
console.log(scope.ngModel);
scope.listing_html = "<tr ng-repeat='user in ngModel'><td>{{user}}</td></tr>"
})
}
};
});
和我的HTML简直就是
And my html is simply
<table my-directive my-options='{"Name": "name", "Email": "email"}' ng-model='userData'></table>
我创建了一个 plunker 一吨的意见,希望有助于解释这个问题。
I've created a plunker with a ton of comments to hopefully help explain the issue.
此问题的非常的类似<一个href=\"http://stackoverflow.com/questions/13141816/angular-js-update-scope-and-template-after-jsonp-request\">this 之一,与解决方案的主要区别不工作。添加 NG-斗篷
雷只是使它不会显示。
这也可能是值得注意的是,我一直在使用这作为参考方式来构造一个指令。
This question is very similar to this one, with the key distinction of that solution not working. Adding ng-cloak
to mine just makes it not display.
It may also be worth noting that I've been using this as reference on the way to construct a directive.
推荐答案
我不是100%肯定,但我相信, ngBindHtml
不会帮助你在这种情况下。结果 ngBindHtml
是用于显示一些正常的HTML,但你要显示一些角,魔术HTML。结果
对于您需要 $编译
的HTML的东西,是角感知和链接
编译后的HTML到一个范围
I am not 100% sure, but I believe that ngBindHtml
will not help you in this case.
ngBindHtml
is for displaying some "normal" HTML, but you want to display some Angular, magic HTML.
For that you need to $compile
the HTML to something that is Angular-aware and link
the compiled HTML to a scope.
我用下面的方法(有明显效果好):
I used the following approach (with apparently good results):
controller: function ($scope, $element, $compile) {
var html = createTmpl(angular.fromJson($scope.myOptions));
$scope.$watch('ngModel', function (newVal) {
var elem = angular.element(html); // Creating element
var linkingFn = $compile(elem); // Compiling element
linkingFn($scope); // Linking element
$element.html(''); // Removing previous content
$element.append(elem); // Inserting new content
// The above is purposedly explicit to highlight what is
// going on. It's moe concise equivalent would be:
//$element.html('').append($compile(html)($scope));
});
其中, createTmpl()
被定义为顾及 myOptions
,并返回相应的模板与创建表一个标题行(根据 myOptions
键)和数据行被定义为 myOptions
属性的值:
where createTmpl()
is defined to take into account myOptions
and return the appropriate template for creating a table with a header-row (based on the keys of myOptions
) and data-rows with the properties defined as myOptions
's values:
function createTmpl(options) {
// Construct the header-row
var html = '<tr>';
angular.forEach(options, function (value, key) {
html += '<th>' + key + '</th>';
});
html += '</tr>\n';
// Construct the data-rows
html += '<tr ng-repeat="user in ngModel">';
angular.forEach(options, function (value, key) {
html += '<td>{{user' + value + '}}</td>';
});
html += '</tr>\n';
// Return the template
return html;
}
又见这个 短演示 结果
<子>
当然,这仅用于演示之用,并不处理一切生产就绪的应用程序应该(例如占错误,缺少的属性,在 myOptions
的变化和诸如此类的东西)。
See, also, this short demo.
Of course, this is for demonstration purposes only and does not handle everything a production-ready app should (e.g. accounting for errors, missing properties, changes in myOptions
and whatnot).
更新
我有非常强的赛区,所以我做了上面,以支持嵌套属性code略有修改。例如。给定的对象具有以下结构:
I had very strong competion, so I did a slight modification of the code above in order to support nested properties. E.g. given an object with the following structure:
user = {
name: 'ExpertSystem',
company: {
name: 'ExpertSystem S.A.',
ranking: 100
}
};
我们可以,只要定义在我们表的列中显示的公司名称 myOptions
是这样的:
we can have the company name displayed in a column of our table, just by defining myOptions
like this:
myOptions='{"Company name": "company.name"}
这篇关于在数据加载角指令模板更新的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!