Angular: Search Tree with highlight match
http://angularjs.org/
by mnk
HTML
<script src="//cdnjs.cloudflare.com/ajax/libs/angular.js/1.2.20/angular.min.js"></script>
<script type="text/ng-template" id="tree_item_renderer.html">
<span ng-click="displayChildren(data)" data-text="data.name" highlight="searchFilter"></span>
<ul>
<li ng-repeat="data in data.nodes | filter: {display: true}" ng-include="'tree_item_renderer.html'"></li>
</ul>
</script>
<ul ng-app="Application" ng-controller="TreeController">
<input type="search" placeholder="Search categories ..." ng-model="searchFilter" ng-change="update()"></input>
<li ng-repeat="data in tree | filter: {display: true}" ng-include="'tree_item_renderer.html'"></li>
</ul>
CSS
body {
margin: 15px;
}
input {
margin-bottom: 10px;
}
ul {
font: 14px/18px Arial;
list-style: circle;
}
li {
list-style: none;
color: #777;
margin-left: 5px;
cursor: pointer;
}
.highlight {
font-weight: bold;
color: black;
}
JavaScript
angular.module("myApp", [])
.controller("TreeController", ['$scope', function($scope) {
$scope.searchFilter = '';
$scope.displayChildren = function(node) {
if (node.nodes) {
for (var i = 0; i < node.nodes.length; i++) {
node.nodes[i].display = !node.nodes[i].display;
}
}
};
function generateGenres(prefix, genreCount, subgenreCount) {
var nodes = [genreCount];
for (var i = 0; i < genreCount; i++) {
nodes[i] = {
name: prefix + '-' + i,
nodes: generateSubGenres(prefix + '-' + i, subgenreCount)
};
}
return nodes;
}
function generateSubGenres(prefix, subgenreCount) {
var nodes = [subgenreCount];
for (var i = 0; i < subgenreCount; i++) {
nodes[i] = {
name: prefix + '-' + i
};
}
return nodes;
}
$scope.tree = [{
name: "Music",
nodes: generateGenres('Music', 10, 25)
}, {
name: "Sports",
nodes: generateGenres('Sports', 10, 25)
}, {
name: "Arts",
nodes: generateGenres('Arts', 10, 25)
}, {
name: "Family",
nodes: generateGenres('Family', 10, 25)
}];
$scope.update = function() {
if ($scope.searchFilter === undefined || $scope.searchFilter.length === 0) {
showOnlyRoots();
} else {
showMatches($scope.searchFilter);
}
};
function showMatches(filter) {
for (var i = 0; i < $scope.tree.length; i++) {
updateSubtree(new RegExp(filter, 'i'), $scope.tree[i]);
}
}
function showOnlyRoots() {
var tree = $scope.tree;
for (var i = 0; i < tree.length; i++) {
tree[i].display = true;
if (tree[i].nodes) {
for (var j = 0; j < tree[i].nodes.length; j++) {
...