我正在构建一个使用Bootstrap Collapse组件来渲染一系列面板的应用程序,所有这些面板最初都处于折叠状态。
由于页面可能包含许多此类面板,并且每个面板可能包含大量内容,因此在用户展开任何面板时,通过执行AJAX调用,按需填充这些面板似乎是合适的。
页面的动态内容(包括面板的标记)是使用AngularJS呈现的,我假设可以将Angular配置为绑定到面板元素上的事件,这会导致其内容在延迟时加载扩大。
不幸的是,在查看了AngularJS文档和可用的教程之后,我看不出如何最好地解决这个问题。任何人都可以对它发光吗?
提前致谢,
添
答案 0 :(得分:2)
它绝对可以改进,但我想这是一个很好的起点。
我已经创建了一个小指令来绑定手风琴面板的click事件。触发click事件后,我通过panel-template=
属性传递了面板模板,并更新了面板中使用的main-template
。
它引用了包含每个面板内容的2个html文件(panel1.html和panel2.html)。
我建议创建一个服务来通过AJAX获取这些文件 - 就像你想要的那样。
在下面的代码中,我为此创建了一个名为dataService
的服务,您应该将其绑定到click
事件 - 因此当用户点击它时,文件会按需加载。
请注意,mainTemplate是所有手风琴的通用面板,所以当它改变时,所有的手风琴将具有相同的内容,但我假设你想要显示只有一个面板,对吗?!
无论如何,正如我之前所说,可以改进逻辑来修复这些小问题,但我相信核心功能是从那里开始的。 :)
<!doctype html>
<html ng-app="myApp">
<head>
<script src="http://code.jquery.com/jquery-1.10.1.min.js"></script>
<script src="http://code.jquery.com/jquery-migrate-1.2.1.min.js"></script>
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.0.8/angular.js"></script>
<script src="//netdna.bootstrapcdn.com/bootstrap/3.0.0/js/bootstrap.min.js"></script>
<link href="//netdna.bootstrapcdn.com/twitter-bootstrap/2.3.1/css/bootstrap-combined.min.css" rel="stylesheet">
<script>
var myApp = angular.module('myApp', []);
myApp.controller('AccordionDemoCtrl', ['$scope', 'dataService', function ($scope, dataService) {
$scope.oneAtATime = true;
$scope.mainTemplate = '';
$scope.groups = [
{
id: "001",
title: "Dynamic Group Header - 1",
content: "Dynamic Group Body - 1",
template: "panel1.html"
},
{
id: "002",
title: "Dynamic Group Header - 2",
content: "Dynamic Group Body - 2",
template: "panel2.html"
}
];
}]);
myApp.factory('dataService', [ '$http', function($http){
return {
getData: function() {
return // you AJAX content data here;
}
}
}]);
myApp.directive('accordionToggle', [function () {
return {
restrict: 'C',
scope: {
mainTemplate: '=',
panelTemplate: '@'
},
link: function (scope, element, iAttrs) {
element.bind('click', function(e){
scope.mainTemplate = scope.panelTemplate;
scope.$apply();
});
}
};
}]);
</script>
</head>
<body ng-controller="AccordionDemoCtrl">
<div class="accordion" id="accordionParent">
<div class="accordion-group" ng-repeat="group in groups" >
<div class="accordion-heading">
<a class="accordion-toggle" main-template="$parent.mainTemplate" panel-template="{{ group.template }}" data-toggle="collapse" data-parent="#accordionParent" href="#collapse{{ $parent.group.id }}">
Collapsible Group Item {{ $parent.group.id }}
</a>
</div>
<div id="collapse{{ group.id }}" class="accordion-body collapse">
<div class="accordion-inner">
<div class="include-example" ng-include="mainTemplate"></div>
</div>
</div>
</div>
</div>
</body>
</html>
答案 1 :(得分:2)
这已经过时了,但问题可能会偶尔出现。我现在发现这是最合适的解决方案而不会污染您的控制器:
(myDirective
在创建后立即通过AJAX加载其内容。)
<accordion>
<accordion-group
heading=""
ng-repeat="foo in bar"
ng-init="status = {load: false}"
ng-click="status.load = true">
<myDirective ng-if="status.load"></myDirective>
</accordion-group>
</accordion>
由ng-repeat
创建的每个元素都有自己的$ scope,因此单击ab accordion-group将导致仅加载相应的指令。
编辑:
根据延迟和延迟加载的数据大小,您可以考虑使用ng-mouseover
而不是ng-click
。这样,在用户打开手风琴之前大约100ms开始加载,这可以减少UI的“迟缓”。显然,偶尔加载从未实际点击过的组内容是不利的。