I am using mat-tree
with mat-nested-tree-node
in Angular 6.
What I want is to load the data dynamically when the user toggles expand icon.
Add Remove Update element with Angular 6 Nested Tree Material
addmodifymilestone.component.ts
import { Component, Injectable, AfterViewInit, ViewChild } from '@angular/core';
import { NestedTreeControl } from '@angular/cdk/tree';
import { MatTreeNestedDataSource } from '@angular/material/tree';
import { BehaviorSubject, Observable, of as observableOf } from 'rxjs';
/**
* Json node data with nested structure. Each node has a filename and a value or a list of children
*/
export class ItemNode {
children: ItemNode[];
filename: string;
type: any;
expanded: boolean;
}
@Component({
selector: 'app-addmodifymilestone',
templateUrl: './addmodifymilestone.component.html',
styleUrls: ['./addmodifymilestone.component.scss'],
})
export class AddmodifymilestoneComponent implements AfterViewInit {
@ViewChild('tree') tree;
updateNodeItemName: any = 'null';
updateItemNameInput: any;
nestedTreeControl: NestedTreeControl;
nestedDataSource: MatTreeNestedDataSource;
dataChange: BehaviorSubject = new BehaviorSubject([]);
constructor() {
this.nestedTreeControl = new NestedTreeControl(this._getChildren);
this.nestedDataSource = new MatTreeNestedDataSource();
this.dataChange.subscribe(data => this.nestedDataSource.data = data);
this.dataChange.next([
// {
// filename: 'Milestones',
// type: '',
// 'expanded': false,
// children: [
// {
// filename: 'Milestone1',
// type: '',
// 'expanded': false,
// children: []
// }
// ]
// }
]);
// this.dataChange.next([
// {
// filename: 'Milestones',
// type: '',
// children: [
// {
// filename: 'Milestone1',
// type: '',
// children: [
// {
// filename: 'To do list',
// type: '',
// children: [
// {
// filename: 'Suggestion',
// type: 'suggetion1, suggestion 2',
// children: []
// }
// ],
// },
// ],
// }
// ],
// },
// ]);
}
private _getChildren = (node: ItemNode) => {
return observableOf(node.children);
}
hasNestedChild = (_: number, nodeData: ItemNode) => {
return !(nodeData.type);
}
ngAfterViewInit(): void {
this.nestedTreeControl = new NestedTreeControl(this._getChildren);
this.nestedDataSource = new MatTreeNestedDataSource();
this.dataChange.subscribe(data => this.nestedDataSource.data = data);
}
changeState(node) {
console.log('change state called :::');
node.expanded = !node.expanded;
console.log(node);
}
addNewMilestone() {
this.nestedTreeControl = new NestedTreeControl(this._getChildren);
this.nestedDataSource = new MatTreeNestedDataSource();
this.dataChange.subscribe(data => this.nestedDataSource.data = data);
let tempData: any[];
this.dataChange.subscribe(data => tempData = data);
const data = new ItemNode();
data.filename = 'New Milestone';
data.type = '',
data.children = [
{
filename: 'AddToDoList',
type: 'AddToDoList',
'expanded': false,
children: [],
},
{
filename: 'To do list',
type: '',
'expanded': false,
children: [
{
filename: 'AddSuggestion',
type: 'AddSuggestion',
'expanded': false,
children: [],
},
{
filename: 'suggestions',
type: 'suggestion1, suggestion2, suggestion3',
'expanded': false,
children: []
},
],
},
];
tempData.push(data);
this.dataChange.next(tempData);
}
addNewToDoList(node: ItemNode) {
this.nestedTreeControl = new NestedTreeControl(this._getChildren);
this.nestedDataSource = new MatTreeNestedDataSource();
this.dataChange.subscribe(data => this.nestedDataSource.data = data);
const nodeChiledren: any[] = node.children;
const data = {
filename: 'To do list',
type: '',
children: [
{
filename: 'AddSuggestion',
type: 'AddSuggestion',
'expanded': false,
children: [],
}
],
};
nodeChiledren.push(data);
let tempData: any[];
this.dataChange.subscribe(data => tempData = data);
tempData = tempData.map((value, index, array) => {
if (value.filename === node.filename) {
value.children = nodeChiledren;
}
return value;
});
const dataStringfy = JSON.stringify(tempData);
const json: ItemNode[] = JSON.parse(dataStringfy);
this.dataChange.next(json);
}
addNewSuggestion(node: ItemNode) {
this.nestedTreeControl = new NestedTreeControl(this._getChildren);
this.nestedDataSource = new MatTreeNestedDataSource();
this.dataChange.subscribe(data => this.nestedDataSource.data = data);
const nodeChiledren: any[] = node.children;
const data = {
filename: 'Suggestion',
type: 'suggestion11, suggestion22',
'expanded': false,
children: [],
};
nodeChiledren.push(data);
let tempData: any[];
this.dataChange.subscribe(data => tempData = data);
tempData = tempData.map((value, index, array) => {
if (value.filename === node.filename) {
value.children = nodeChiledren;
}
return value;
});
const dataStringfy = JSON.stringify(tempData);
const json: ItemNode[] = JSON.parse(dataStringfy);
this.dataChange.next(json);
}
enableUpdateNode(node: ItemNode) {
console.log('updateNode :::');
console.log(node);
this.updateNodeItemName = node.filename;
}
updateNode(node: ItemNode) {
this.updateNodeItemName = 'null';
console.log(this.updateItemNameInput);
console.log(node);
this.nestedTreeControl = new NestedTreeControl(this._getChildren);
this.nestedDataSource = new MatTreeNestedDataSource();
this.dataChange.subscribe(data => this.nestedDataSource.data = data);
node.filename = this.updateItemNameInput;
let tempData: any[];
this.dataChange.subscribe(data => tempData = data);
tempData = tempData.map((value, index, array) => {
if (value.filename === node.filename) {
value = node;
}
return value;
});
const dataStringfy = JSON.stringify(tempData);
const json: ItemNode[] = JSON.parse(dataStringfy);
this.dataChange.next(json);
}
deleteNode(node: any) {
this.nestedTreeControl = new NestedTreeControl(this._getChildren);
this.nestedDataSource = new MatTreeNestedDataSource();
this.dataChange.subscribe(data => this.nestedDataSource.data = data);
node.filename = this.updateItemNameInput;
let tempData: any[];
this.dataChange.subscribe(data => tempData = data);
const index = tempData.findIndex(value => value.filename === node.filename);
tempData.splice(index, 1);
const dataStringfy = JSON.stringify(tempData);
const json: ItemNode[] = JSON.parse(dataStringfy);
this.dataChange.next(json);
}
}
addmodifymilestone.component.html
Add New Milestone
-
{{node.filename}}: {{node.type }}
-
{{node.filename}}
Add To do list
Add Suggestion
addmodifymilestone.component.scss
.example-tree-invisible {
display: none;
}
.example-tree ul,
.example-tree li {
margin-top: 0;
margin-bottom: 0;
list-style-type: none;
}
.example-tree li {
margin-left: 25px;
}
.fa {
margin:5px;
}
.fa-trash{
color: red;
}
.mat-tree-node {
display: flex;
align-items: center;
min-height: 0px;
flex: 1;
overflow: hidden;
word-wrap: break-word;
}
.paragraphMargingLeft{
margin-left: 46px;
}