Skip to content

Commit 11a2528

Browse files
authored
Merge pull request #28135 from nextcloud/backport/28133/stable22
[stable22] add an option to the multiple files selected actions to add and remov…
2 parents c0f3fcd + 377942d commit 11a2528

File tree

3 files changed

+148
-0
lines changed

3 files changed

+148
-0
lines changed

apps/files/css/files.scss

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1215,3 +1215,25 @@ table.dragshadow td.size {
12151215
#gallery-button {
12161216
display: none;
12171217
}
1218+
1219+
#tag_multiple_files_container {
1220+
overflow: hidden;
1221+
background-color: #fff;
1222+
border-radius: 3px;
1223+
position: relative;
1224+
display: flex;
1225+
flex-wrap: wrap;
1226+
margin-bottom: 10px;
1227+
1228+
h3 {
1229+
width: 100%;
1230+
padding: 0 18px;
1231+
}
1232+
1233+
.systemTagsInputFieldContainer {
1234+
flex: 1 1 80%;
1235+
min-width: 0;
1236+
margin: 0 12px;
1237+
}
1238+
}
1239+

apps/files/js/app.js

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -113,6 +113,11 @@
113113
iconClass: 'icon-delete',
114114
order: 99,
115115
},
116+
{
117+
name: 'tags',
118+
displayName: 'Tags',
119+
iconClass: 'icon-tag'
120+
},
116121
],
117122
sorting: {
118123
mode: $('#defaultFileSorting').val(),

apps/files/js/filelist.js

Lines changed: 121 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -555,6 +555,9 @@
555555
case 'restore':
556556
this._onClickRestoreSelected(ev);
557557
break;
558+
case 'tags':
559+
this._onClickTagSelected(ev);
560+
break;
558561
}
559562
},
560563
/**
@@ -1116,6 +1119,124 @@
11161119
event.preventDefault();
11171120
},
11181121

1122+
/**
1123+
* CUSTOM CODE
1124+
* Event handler for when clicking on "Tags" for the selected files
1125+
*/
1126+
_onClickTagSelected: function(event) {
1127+
var self = this;
1128+
event.preventDefault();
1129+
var commonTags = [];
1130+
1131+
var selectedFiles = _.pluck(this.getSelectedFiles(), 'id')
1132+
var tagCollections = [];
1133+
var fetchTagPromises = [];
1134+
1135+
1136+
selectedFiles.forEach(function(fileId) {
1137+
var deferred = new $.Deferred();
1138+
var tagCollection = new OC.SystemTags.SystemTagsMappingCollection([], {
1139+
objectType: 'files',
1140+
objectId: fileId});
1141+
tagCollections.push(tagCollection);
1142+
tagCollection.fetch({
1143+
success: function(){
1144+
deferred.resolve('success');
1145+
},
1146+
error: function() {
1147+
deferred.resolve('failed');
1148+
}
1149+
})
1150+
fetchTagPromises.push(deferred);
1151+
});
1152+
1153+
if (!self._inputView) {
1154+
self._inputView = new OC.SystemTags.SystemTagsInputField({
1155+
multiple: true,
1156+
allowActions: true,
1157+
allowCreate: true,
1158+
isAdmin: OC.isUserAdmin(),
1159+
});
1160+
self._inputView.on('select', self._onSelectTag, self);
1161+
self._inputView.on('deselect', self._onDeselectTag, self);
1162+
self._inputView.render();
1163+
1164+
// Build dom
1165+
self.tagsTitle = $('<h3>'+ t('files', 'Please select tag(s) to add to the selection') +'</h3>');
1166+
self.tagsSubmit = $('<button>' + t('files', 'Apply tag(s) to selection') + '</button>');
1167+
self.tagsContainer = $('<tr id="tag_multiple_files_container"></tr>');
1168+
self.tagsTitle.appendTo(self.tagsContainer)
1169+
self.tagsContainer.append(self._inputView.el);
1170+
self.tagsSubmit.appendTo(self.tagsContainer)
1171+
1172+
// Inject everything
1173+
self.$table.find('thead').append(self.tagsContainer);
1174+
1175+
self.tagsSubmit.on('click', function(ev){
1176+
self._onClickDocument(ev);
1177+
});
1178+
}
1179+
1180+
self._inputView.$el.addClass('icon-loading');
1181+
self.tagsContainer.show();
1182+
1183+
Promise.all(fetchTagPromises).then(function() {
1184+
//find tags which are common to all selected files
1185+
commonTags =_.intersection.apply(null, tagCollections.map(function (tagCollection) {return tagCollection.getTagIds();}));
1186+
self._inputView.setValues(commonTags);
1187+
self._inputView.$el.removeClass('icon-loading');
1188+
$(document).on('click',function(ev){
1189+
self._onClickDocument(ev);
1190+
});
1191+
});
1192+
},
1193+
1194+
_onClickDocument: function(ev) {
1195+
if(!$(ev.target).closest('#editor_container').length) {
1196+
this._inputView.setValues([]);
1197+
this.tagsContainer.hide();
1198+
$(document).off('click', this._onClickDocument);
1199+
}
1200+
1201+
},
1202+
1203+
/**
1204+
* Custom code
1205+
* Set tag for all selected files
1206+
* @param tagModel
1207+
* @private
1208+
*/
1209+
_onSelectTag: function(tagModel) {
1210+
var selectedFiles = _.pluck(this.getSelectedFiles(),'id')
1211+
if (!_.isArray(selectedFiles)) {
1212+
return;
1213+
}
1214+
selectedFiles.forEach(function(fileId) {
1215+
$.ajax({
1216+
url: OC.linkToRemote('dav') + '/systemtags-relations/files/' + fileId + '/'+ tagModel.attributes.id,
1217+
type: 'PUT',
1218+
});
1219+
});
1220+
1221+
},
1222+
/**
1223+
* remove tag from all selected files
1224+
* @param tagId
1225+
* @private
1226+
*/
1227+
_onDeselectTag: function(tagId) {
1228+
var selectedFiles = _.pluck(this.getSelectedFiles(),'id');
1229+
if (!_.isArray(selectedFiles)) {
1230+
return;
1231+
}
1232+
selectedFiles.forEach(function(fileId) {
1233+
$.ajax({
1234+
url: OC.linkToRemote('dav') + '/systemtags-relations/files/' +fileId + '/'+ tagId,
1235+
type: 'DELETE'
1236+
});
1237+
});
1238+
},
1239+
11191240
/**
11201241
* Event handler when clicking on a table header
11211242
*/

0 commit comments

Comments
 (0)