change some code for better perfomance, support indeterminate

This commit is contained in:
vitam 2017-07-27 22:31:33 +02:00
parent 2b6fe4b2bd
commit caa1e940e2
3 changed files with 92 additions and 47 deletions

View File

@ -1031,7 +1031,7 @@
</script> </script>
<!-- }}} --> <!-- }}} -->
<!-- {{{ select files checkbox modal --> <!-- {{{ select files checkbox modal -->
<script type="text/ng-template" id="selectFilesCheckBox.html"> <script type="text/ng-template" id="selectFilesCheckBox.html">
<div ng-repeat="(folderName,folder) in files.dirs"> <div ng-repeat="(folderName,folder) in files.dirs">
<!--recursive folder--> <!--recursive folder-->
@ -1040,7 +1040,7 @@
<!--click to toggle show the subfolders and files--> <!--click to toggle show the subfolders and files-->
<div class="checkbox" data-ng-click="folder.show=!folder.show"> <div class="checkbox" data-ng-click="folder.show=!folder.show">
<!-- The value of indeterminate="" can be bound to any angular expression --> <!-- The value of indeterminate="" can be bound to any angular expression -->
<input type="checkbox" ng-model="folder.selected" data-ng-click="$event.stopPropagation()" indeterminate="true"/>{{folderName}} <input type="checkbox" ng-model="folder.selected" data-ng-click="$event.stopPropagation()" indeterminate="folder.indeterminate" monitor/>{{folderName}}
<span ng-show="!folder.show" class="control-label">{{ 'click the text to expand the folder' | translate }}</span> <span ng-show="!folder.show" class="control-label">{{ 'click the text to expand the folder' | translate }}</span>
<span ng-show="folder.show" class="control-label">{{ 'click the text to collapse the folder' | translate }}</span> <span ng-show="folder.show" class="control-label">{{ 'click the text to collapse the folder' | translate }}</span>
</div> </div>
@ -1055,7 +1055,7 @@
<div class="controls"> <div class="controls">
<label class="checkbox"> <label class="checkbox">
<input type="checkbox" ng-model="file.selected"/>{{file.relpath}} <input type="checkbox" ng-model="file.selected" monitor/>{{file.relpath}}
</label> </label>
</div> </div>
<br/> <br/>

View File

@ -124,56 +124,65 @@ angular
this.files = _.cloneDeep(files); this.files = _.cloneDeep(files);
var groupFiles = function (files) { var groupFiles = function (files) {
var createSubFolder = function () { function OrganizedFolder () {
var folder = { this.dirs = {};
dirs : {}, this.files = [];
files : {}, this.show = false;
show : false, this._selected = false;
_selected : false, }
change : function () { OrganizedFolder.prototype.change = function () {
for (var file in this.files) { for (var i = 0; i < this.files.length; i++) {
if (this.files.hasOwnProperty(file)) { this.files[i].selected = this.selected;
this.files[file].selected = this.selected; }
} for (var folder in this.dirs) {
} if (this.dirs.hasOwnProperty(folder)) {
for (var folder in this.dirs) { this.dirs[folder].selected = this.selected;
if (this.dirs.hasOwnProperty(folder)) {
this.dirs[folder].selected = this.selected;
}
}
console.log(this);
} }
}; }
Object.defineProperty(folder, "selected", {
get : function () {
return this._selected;
},
set : function (newValue) {
this._selected = newValue;
this.change();
}
});
Object.defineProperty(folder, "indeterminate", {
get : function () {
return this._selected;
}
});
return folder;
}; };
var folder = createSubFolder(), Object.defineProperty(OrganizedFolder.prototype, "selected", {
tmp; get : function () {
return this._selected;
},
set : function (newValue) {
this._selected = newValue;
this.change();
}
});
Object.defineProperty(OrganizedFolder.prototype, "indeterminate", {
get : function () {
var allSeleted = true;
var allNotSelected = true;
for (var p in this.dirs) {
if (this.dirs.hasOwnProperty(p)) {
if (this.dirs[p].indeterminate) {
return true;
}
allSeleted &= this.dirs[p].selected;
allNotSelected &= !this.dirs[p].selected;
}
}
for (var i = 0; i < this.files.length; i++) {
allSeleted &= this.files[i].selected;
allNotSelected &= !this.files[i].selected;
}
return !allSeleted && !allNotSelected;// is not determinate when either all selected either all not selected;
}
});
var folder = new OrganizedFolder(), tmp;
for (var i = 0; i < files.length; i++) { for (var i = 0; i < files.length; i++) {
tmp = folder; tmp = folder;
var str = files[i].relpath; var str = files[i].relpath;
var arr = str.split("/"); var arr = str.split("/");
for (var j = 0; j < arr.length - 1; j++) { for (var j = 0; j < arr.length - 1; j++) {
if (!tmp.dirs[arr[j]]) { if (!tmp.dirs[arr[j]]) {
tmp.dirs[arr[j]] = createSubFolder(); tmp.dirs[arr[j]] = new OrganizedFolder();
} }
tmp = tmp.dirs[arr[j]]; tmp = tmp.dirs[arr[j]];
} }
tmp.files[arr[arr.length - 1]] = files[i]; tmp.files.push(files[i]);
} }
folder.change();
return folder; return folder;
}; };
this.groupedFiles = groupFiles(this.files); this.groupedFiles = groupFiles(this.files);

View File

@ -1,6 +1,7 @@
// watches changes in the file upload control (input[file]) and // watches changes in the file upload control (input[file]) and
// puts the files selected in an attribute // puts the files selected in an attribute
angular.module("webui.directives.fileselect", []).directive("indeterminate", function () { var app = angular.module("webui.directives.fileselect", []);
app.directive("indeterminate", function () {
return { return {
// Restrict the directive so it can only be used as an attribute // Restrict the directive so it can only be used as an attribute
restrict : "A", restrict : "A",
@ -8,13 +9,48 @@ angular.module("webui.directives.fileselect", []).directive("indeterminate", fun
link : function link (scope, elem, attr) { link : function link (scope, elem, attr) {
// Whenever the bound value of the attribute changes we update // Whenever the bound value of the attribute changes we update
// the internal 'indeterminate' flag on the attached dom element // the internal 'indeterminate' flag on the attached dom element
var watcher = scope.$watch(attr.indeterminate, function (value) { // use upward emit notification for change to prevent the performance penalty bring by $scope.$watch
elem[0].indeterminate = value; elem[0].indeterminate = scope.$eval(attr.indeterminate);
scope.$on("childSelectedChange", function (event, options) {
elem[0].indeterminate = scope.$eval(attr.indeterminate);
}); });
// Remove the watcher when the directive is destroyed /* var watcher = scope.$watch(attr.indeterminate, function (value) {
scope.$on("$destroy", function () { elem[0].indeterminate = value;
watcher(); });
// Remove the watcher when the directive is destroyed
scope.$on("$destroy", function () {
watcher();
}); */
}
};
});
app.directive("monitor", function () {
return {
// Restrict the directive so it can only be used as an attribute
restrict : "A",
link : function link (scope, elem, attr) {
// Whenever the bound value of the attribute changes we update
// the internal 'indeterminate' flag on the attached dom element
elem.change(function () {
scope.$emit("childSelectedChange");
});
}
};
});
app.directive("selected", function () {
return {
// Restrict the directive so it can only be used as an attribute
restrict : "A",
link : function link (scope, elem, attr) {
elem[0].value = scope.$eval(attr.selected);
scope.$on("childSelectedChange", function (event, options) {
elem[0].value = scope.$eval(attr.selected);
}); });
} }
}; };