Working on this AngularJs(1.4) code snippet and need help to get recursive tree view to work as desired.
It currently has 4 levels, and what is needed is:
- When I open a folder, it should close all folders of same level( including their children and sub-children).
It works for level 2 folders, but not for deeper level 3,4 or even N levels.
Refactoring is also ok using say a Angular Tree view, or something pretty light to achieve same results.
Full Plunker code: https://plnkr.co/edit/vacr1E1sy40mCdSrjW7R?p=preview .
some code:
onClickFolder: function(paramFolderId) {
var targetFolderParent = document.getElementById('folder' + paramFolderId) || null;
var parentFolderWithChild = document.getElementById('parentFolder' + paramFolderId) || null;
if (parentFolderWithChild !== null) {
// collapse all children except active
var allChildNodes = document.querySelectorAll(".child");
console.log("all child", allChildNodes)
var childElement = document.getElementById(paramFolderId);
_fnc.collapseAllChildNodes(allChildNodes, paramFolderId);
_fnc.toggleTreeView(childElement);
}
if (targetFolderParent !== null) {
var strClass = targetFolderParent.getAttribute('class');
var selector = "#companyStructureBlock ul i";
_fnc.removeAllIsOpened(targetFolderParent, selector);
targetFolderParent.setAttribute('class', strClass + ' isOpened');
}
},
collapseAllChildNodes: function(allChildNodes, paramFolderId) {
for (i = 0; i < allChildNodes.length; i++) {
var node = angular.element(allChildNodes[i]);
console.log("angular node", node, allChildNodes[i])
if (node.context.id !== "folder" + paramFolderId) {
node.removeClass("expand-folder");
node.addClass("collapse-folder");
} else {
node.addClass("expand-folder");
}
}
},
removeAllIsOpened: function(targetFolderParent, selector) {
//remove all other isOpened class before setting the currentTarget
var allNodes = document.querySelectorAll(selector);
for (var i = 0; i < allNodes.length; i++) {
var node = angular.element(allNodes[i]);
if (targetFolderParent.dataset.level == angular.element(allNodes[i]).context.dataset.level) {
node.removeClass('isOpened');
console.log("here remove all", angular.element(angular.element(node).find("ul .child")).children());
}
}
},
toggleTreeView: function(childElement) {
var collapse = angular.element(childElement).hasClass('collapse-folder');
var expand = angular.element(childElement).hasClass('expand-folder');
if (!expand && !collapse) {
angular.element(childElement).addClass("expand-folder");
} else if (expand & !collapse) {
angular.element(childElement).removeClass("expand-folder");
angular.element(childElement).addClass("collapse-folder");
} else if (!expand & collapse) {
angular.element(childElement).removeClass("collapse-folder");
angular.element(childElement).addClass("expand-folder");
} else if (expand && collapse) {
angular.element(childElement).removeClass("collapse-folder");
angular.element(childElement).addClass("expand-folder");
} else {
angular.element(childElement).addClass("expand-folder");
}
},
};
<!DOCTYPE html>
<html ng-app="app">
<head>
<script data-require="lodash.js@*" data-semver="2.4.1" src="http://cdnjs.cloudflare.com/ajax/libs/lodash.js/2.4.1/lodash.js"></script>
<script src='https://ajax.googleapis.com/ajax/libs/jquery/1.7.0/jquery.min.js'></script>
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.1/css/bootstrap.min.css" />
<link rel="stylesheet" href="https://use.fontawesome.com/releases/v5.8.1/css/all.css" />
<link href="style.css" rel="stylesheet">
</head>
<body ng-controller='Ctrl'>
<!-- do stuff -->
<h1>{{title}}</h1>
<style>
#companyStructureBlock {
height: 500px;
max-width: 259px;
overflow: auto;
color: #eee;
resize: horizontal;
}
.gridtable tbody tr td {
padding: 0;
}
.gridtable tbody tr td .col-sm-12 {
padding: 0;
}
.expand-folder {
display: block;
}
.collapse-folder {
display: none;
}
</style>
<div id="companyStructureBlock">
<div>
Structures
</div>
<br>
<i id="folder{{structure.folderId}}" ng-class="companyStructure.rootStructure.blnIsOpened? 'isOpened' : '' " class="fas fa-folder folder" src="{{ui.img.companyStructure.folder}}"> <a ng-click="loadOnDemand($event, companyStructure.rootStructure.folderId,1);filterContactsBasedOnFolder(companyStructure.rootStructure.folderId);"
class="mrm" ng-bind="companyStructure.rootStructure.levelName | limitTo:20:' ...'"></a></i>
<ul ng-repeat="structure in structureData | orderBy: ['-unassignedSubstructure','folderId']" id="parentFolder{{structure.folderId}}">
<i id="folder{{structure.folderId}}" class="fas fa-folder folder" src="{{ui.img.companyStructure.folderplus}}" data-level="{{structure.level}}">
<a ng-click="loadOnDemand($event,structure.folderId,structure.level);filterContactsBasedOnFolder(structure.folderId);" class="mrm"
ng-bind="structure.levelName"></a></i>
<ul id="{{structure.folderId}}" class="child">
</ul>
</ul>
<br>
<i id="folder{{structure.folderId}}" class="fas">
<a ng-click="loadOnDemand($event, companyStructure.rootStructure.folderId,1);filterContactsBasedOnFolder(companyStructure.rootStructure.folderId);"
class="mrm">Return to All Contacts</a></i>
</div>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.14/angular.min.js"></script>
<script src="http://angular-ui.github.io/bootstrap/ui-bootstrap-tpls-0.13.4.js"></script>
<script src="app.js"></script>
<script src="factory.js"></script>
<script src="controller.js"></script>
</body>
</html>