1 {% extends "page.html.twig" %}
3 {% set can_export = login.isGroupManager() and preferences.pref_bool_groupsmanagers_exports or login.isAdmin() or login.isStaff() %}
5 {% macro group_item(login, group, opened, selected) %}
6 <div class="{% if group.getGroups()|length > 0 %}title{% if group.getName() in opened %} active{% endif %}{% else %}nochild{% endif %}">
7 <i class="{% if group.getGroups()|length > 0 %}dropdown{% else %}empty{% endif %} icon" aria-hidden="true"></i>
8 <a class="ui{% if group.getName() == selected %} primary{% endif %}{% if not login.isGroupManager(group.getId()) %} disabled{% endif %} label" href="{% if login.isGroupManager(group.getId()) %}{{ url_for("groups", {"id": group.getId()}) }}{% else %}#{% endif %}">
12 {% if group.getGroups()|length > 0 %}
13 <div class="content{% if group.getName() in opened %} active{% endif %}">
14 <div class="accordion">
15 {% for child_group in group.getGroups() %}
16 {{ _self.group_item(login, child_group, opened, selected) }}
24 {% set opened = group.getFullName()|split(' / ') %}
25 {% set selected = opened|last %}
26 <div class="ui stackable grid">
27 <div class="three wide column">
28 {% if group.getId() %}
29 <div class="ui top attached accordion-styled header">{{ _T("Select a group") }} :</div>
30 <div class="ui attached accordion-styled scrolling segment loader_selector">
31 <div class="ui tree accordion">
32 {% for group in groups_root %}
33 {{ _self.group_item(login, group, opened, selected) }}
38 {% if can_export or login.isAdmin() or login.isStaff() %}
39 <div class="ui basic fitted segment">
40 <div class="ui wrapping spaced buttons">
41 {% if group.getId() and can_export %}
42 <a href="{{ url_for("pdf_groups") }}" class="ui labeled icon fluid button tooltip" title="{{ _T("Export all groups and their members as PDF") }}">
43 <i class="file pdf red labeled icon" aria-hidden="true"></i>
44 {{ _T("All groups PDF") }}
47 {% if login.isAdmin() or login.isStaff() %}
48 <a href="{{ url_for("add_group", {"name": "NAME"}) }}" class="ui labeled icon fluid button tooltip" id="newgroup" title="{{ _T("New group") }}">
49 <i class="plus circle green icon" aria-hidden="true"></i>
57 <div class="thirteen wide column">
58 {% if group.getId() %}
59 {% include "elements/group.html.twig" with {"group": group, "parent_groups": parent_groups} %}
67 {% block javascripts %}
68 <script type="text/javascript">
73 $('#newgroup').click(function(){
74 var _href = $(this).attr('href');
75 var _input = '<div class="ui labeled input"><div class="ui label">{{ _T("Name:") }}</div><input type="text" name="new_group_name" id="new_group_name" required/></div>';
77 title: '{{ _T("Add a new group") }}',
80 onApprove: function() {
81 var _name = $('#new_group_name').val();
85 url: '{{ url_for("ajax_groupname_unique") }}',
91 {% include "elements/js/loader.js.twig" with {
92 selector: ".segment:not(.tab).loader_selector",
95 success: function(res){
96 if ( res.success == false ) {
98 {% include "elements/js/modal.js.twig" with {
99 modal_title_twig: _T("An error occurred :(")|e("js"),
100 modal_content: "res.message",
102 modal_content_class: "scrolling",
103 modal_deny_only: true,
104 modal_cancel_text: _T("Close")|e("js"),
105 modal_classname: "redalert",
108 {% include "elements/js/modal.js.twig" with {
109 modal_title_twig: _T("The group name you have requested already exists in the database.")|e("js"),
110 modal_without_content: true,
112 modal_deny_only: true,
113 modal_cancel_text: _T("Close")|e("js"),
114 modal_classname: "redalert",
118 $(location).attr('href', _href.replace('NAME', _name));
122 {% include "elements/js/modal.js.twig" with {
123 modal_title_twig: _T("An error occurred checking name uniqueness :(")|e("js"),
124 modal_without_content: true,
126 modal_deny_only: true,
127 modal_cancel_text: _T("Close")|e("js"),
128 modal_classname: "redalert",
133 {% include "elements/js/modal.js.twig" with {
134 modal_title_twig: _T("Please provide a group name")|e("js"),
135 modal_without_content: true,
137 modal_deny_only: true,
138 modal_cancel_text: _T("Close")|e("js"),
139 modal_classname: "redalert",
145 text : '{{ _T("Create")|e('js') }}',
147 class : 'icon labeled green approve'
149 text : '{{ _T("Close")|e('js') }}',
151 class : 'icon labeled deny'
158 var _btnuser_mapping = function(){
159 $('#btnusers_small, #btnmanagers_small').click(function(){
160 _mode = ($(this).attr('id') == 'btnusers_small') ? 'members' : 'managers';
161 var _persons = $('input[name="' + _mode + '[]"]').map(function() {
162 return $(this).val();
165 url: '{{ url_for('ajaxMembers') }}',
170 gid: $('#id_group').val(),
174 {% include "elements/js/loader.js.twig" with {
176 selector: ".tab.segment.active .loader_selector"
178 success: function(res){
179 _members_dialog(res, _mode);
182 {% include "elements/js/modal.js.twig" with {
183 modal_title_twig: _T("An error occurred displaying members interface :(")|e("js"),
184 modal_without_content: true,
186 modal_deny_only: true,
187 modal_cancel_text: _T("Close")|e("js"),
188 modal_classname: "redalert",
197 var _members_dialog = function(res, mode){
198 var _title = '{{ _T("Group members selection")|e('js') }}';
199 if ( mode == 'managers' ) {
200 _title = '{{ _T("Group managers selection")|e('js') }}';
202 {% include "elements/js/modal.js.twig" with {
203 modal_title: "_title",
204 modal_content: "res",
205 modal_class: "members-selection fullscreen",
206 modal_content_class: "scrolling",
207 modal_deny_only: true,
208 modal_cancel_text: _T("Close")|e("js"),
209 modal_other_options: {
213 _members_ajax_mapper(res, $('#group_id').val(), mode);
217 var _members_ajax_mapper = function(res, gid, mode){
218 $('#btnvalid').click(function(){
219 //store entities in the original page so they can be saved
221 if ( mode == 'managers' ) {
222 _container = $('#group_managers');
224 _container = $('#group_members');
226 var _persons = new Array();
227 $('li[id^="member_"]').each(function(){
228 _persons[_persons.length] = this.id.substring(7, this.id.length);
230 if ( _persons.length == 0 ) {
234 url: '{{ url_for('ajaxGroupMembers') }}',
240 {% include "elements/js/loader.js.twig" with {
241 selector: "#btnvalid",
244 success: function(res){
245 var _modified = '<div class="ui icon yellow small message with-transition"><i class="exclamation triangle icon" aria-hidden="true"></i><div class="content">{{ _T("Items in this list have been modified. Don't forget to save your changes.")|e('js') }}</div></div>';
246 _container.find('.message').remove();
248 _container.find('.loader_selector').remove();
249 _container.children('.segment').append(res);
250 _container.children('#group_' + mode + ' .segment').append(_modified);
252 var _emptyselection = '<tbody><tr><td colspan="2"><input type="hidden" name="' + mode + '[]" value="">{{ _T("No member attached")|e('js') }}</td></tr></tbody>';
253 _container.find('table.listing tbody').remove();
254 _container.find('table.listing').append(_emptyselection);
255 _container.children('#group_' + mode + ' .segment').append(_modified);
257 $('.members-selection').modal('hide');
258 $('.message.with-transition').transition('flash');
261 {% include "elements/js/modal.js.twig" with {
262 modal_title_twig: _T("An error occurred displaying members interface :(")|e("js"),
263 modal_without_content: true,
265 modal_deny_only: true,
266 modal_cancel_text: _T("Close")|e("js"),
267 modal_classname: "redalert",
274 var _none = $('#none_selected').clone();
275 $('li[id^="member_"]').click(function(){
277 if ( $('#selected_members ul li').length == 0 ) {
278 $('#selected_members ul').append(_none);
282 $('#listing tbody tr').click(function(event){
283 event.preventDefault();
284 var _mlink = $(this).find('.username_row a');
285 var _mid = _mlink[0].href.match(/.*\/(\d+)$/)[1];
286 var _mname = _mlink.text();
287 $('#none_selected').remove()
288 if ( $('#member_' + _mid).length == 0 ) {
289 var _li = '<li id="member_' + _mid + '" class="item"><i class="ui user minus icon" aria-hidden="true"></i><span class="ui content">' + _mname + '</span></li>';
290 $('#selected_members ul').append(_li);
291 $('#member_' + _mid).click(function(){
293 if ( $('#selected_members ul li').length == 0 ) {
294 $('#selected_members ul').append(_none);
299 }).css('cursor', 'pointer').attr('title', '{{ _T("Click on a row to select a member")|e('js') }}');
301 $('.members-selection .pagination a').click(function(){
302 var gid = $('#the_id').val();
303 var _members = new Array();
304 $('li[id^="member_"]').each(function(){
305 _members[_members.length] = this.id.substring(7, this.id.length);
318 {% include "elements/js/loader.js.twig" with {
321 success: function(res){
322 $('#listing').remove();
323 var _listing = $($.parseHTML(res)).find('#listing');
324 $('.members-selection .eleven.wide.column').prepend(_listing);
325 _members_ajax_mapper(res, gid, _mode);
328 {% include "elements/js/modal.js.twig" with {
329 modal_title_twig: _T("An error occurred displaying members interface :(")|e("js"),
330 modal_without_content: true,
332 modal_deny_only: true,
333 modal_cancel_text: _T("Close")|e("js"),
334 modal_classname: "redalert",
342 {% include "elements/js/removal.js.twig" with {
344 loader_selector: "#delete",
345 single_action: "true"