diff --git a/mayan/apps/appearance/static/appearance/css/base.css b/mayan/apps/appearance/static/appearance/css/base.css index 0cb7944b43..3c70bd2e8c 100644 --- a/mayan/apps/appearance/static/appearance/css/base.css +++ b/mayan/apps/appearance/static/appearance/css/base.css @@ -220,6 +220,18 @@ a i { font-weight: bold; } +.panel-highlighted { + box-shadow: 0px 0px 3px #18bc9c, 10px 10px 20px #000000; +} + +.panel-highlighted:hover { + box-shadow: 0px 0px 3px #18bc9c, 10px 10px 20px #000000, 0px 0px 8px #000000; +} + +.panel-item:not(.panel-highlighted):hover { + box-shadow: 0px 0px 8px #000000; +} + /* Content */ @media (min-width:1200px) { .container-fluid { @@ -249,14 +261,6 @@ a i { margin: auto; } -.thin_border { - border: 1px solid black; - display: block; - margin-left: auto; - margin-right: auto; -} - - .thin_border-thumbnail { display: block; max-width: 100%; @@ -266,6 +270,14 @@ a i { margin: auto; } +/* Must go after .thin_border-thumbnail */ +.thin_border { + border: 1px solid black; + display: inline; + margin-left: 0px; + margin-right: 0px; +} + #ajax-spinner { position: fixed; top: 16px; diff --git a/mayan/apps/appearance/static/appearance/js/base.js b/mayan/apps/appearance/static/appearance/js/base.js index 244ac0298a..ff87e82871 100644 --- a/mayan/apps/appearance/static/appearance/js/base.js +++ b/mayan/apps/appearance/static/appearance/js/base.js @@ -6,7 +6,8 @@ var MayanAppClass = MayanApp; var partialNavigation = new PartialNavigation({ initialURL: initialURL, - disabledAnchorClasses: ['disabled'], + disabledAnchorClasses: [ + 'btn-multi-item-action', 'disabled', 'pagination-disabled' + ], excludeAnchorClasses: ['fancybox', 'new_window', 'non-ajax'], - formBeforeSerializeCallbacks: [MayanApp.MultiObjectFormProcess], }); diff --git a/mayan/apps/appearance/static/appearance/js/mayan_app.js b/mayan/apps/appearance/static/appearance/js/mayan_app.js index d96c7f4c9b..acbeeb1283 100644 --- a/mayan/apps/appearance/static/appearance/js/mayan_app.js +++ b/mayan/apps/appearance/static/appearance/js/mayan_app.js @@ -17,30 +17,36 @@ class MayanApp { // Class methods and variables - static MultiObjectFormProcess ($form, options) { - /* - * ajaxForm callback to add the external item checkboxes to the - * submitted form - */ + static countChecked() { + var checkCount = $('.check-all-slave:checked').length; - if ($form.hasClass('form-multi-object-action')) { - // Turn form data into an object - var formArray = $form.serializeArray().reduce(function (obj, item) { - obj[item.name] = item.value; - return obj; - }, {}); - - // Add all checked checkboxes to the form data - $('.form-multi-object-action-checkbox:checked').each(function() { - var $this = $(this); - formArray[$this.attr('name')] = $this.attr('value'); - }); - - // Set the form data as the data to send - options.data = formArray; + if (checkCount) { + $('#multi-item-title').hide(); + $('#multi-item-actions').show(); + } else { + $('#multi-item-title').show(); + $('#multi-item-actions').hide(); } } + static setupMultiItemActions () { + $('body').on('change', '.check-all-slave', function () { + MayanApp.countChecked(); + }); + + $('body').on('click', '.btn-multi-item-action', function (event) { + var id_list = []; + $('.check-all-slave:checked').each(function (index, value) { + //Split the name (ie:"pk_200") and extract only the ID + id_list.push(value.name.split('_')[1]); + }); + event.preventDefault(); + partialNavigation.setLocation( + $(this).attr('href') + '?id_list=' + id_list.join(',') + ); + }); + } + static setupNavBarState () { $('body').on('click', '.a-main-menu-accordion-link', function (event) { console.log('ad'); @@ -166,10 +172,10 @@ class MayanApp { var self = this; this.setupAJAXSpinner(); - this.setupAutoSubmit(); this.setupFormHotkeys(); this.setupFullHeightResizing(); this.setupItemsSelector(); + MayanApp.setupMultiItemActions(); this.setupNavbarCollapse(); MayanApp.setupNavBarState(); this.setupNewWindowAnchor(); @@ -177,6 +183,7 @@ class MayanApp { value.app = self; app.doRefreshAJAXMenu(value); }); + this.setupPanelSelection(); partialNavigation.initialize(); } @@ -200,14 +207,6 @@ class MayanApp { }); } - setupAutoSubmit () { - $('body').on('change', '.select-auto-submit', function () { - if ($(this).val()) { - $(this.form).trigger('submit'); - } - }); - } - setupFormHotkeys () { $('body').on('keypress', '.form-hotkey-enter', function (e) { if ((e.which && e.which == 13) || (e.keyCode && e.keyCode == 13)) { @@ -238,9 +237,22 @@ class MayanApp { app.lastChecked = null; $('body').on('click', '.check-all', function (event) { + var $this = $(this); var checked = $(event.target).prop('checked'); var $checkBoxes = $('.check-all-slave'); + if (checked === undefined) { + checked = $this.data('checked'); + checked = !checked; + $this.data('checked', checked); + + if (checked) { + $this.find('[data-fa-i2svg]').addClass($this.data('icon-checked')).removeClass($this.data('icon-unchecked')); + } else { + $this.find('[data-fa-i2svg]').addClass($this.data('icon-unchecked')).removeClass($this.data('icon-checked')); + } + } + $checkBoxes.prop('checked', checked); $checkBoxes.trigger('change'); }); @@ -286,6 +298,58 @@ class MayanApp { }); } + setupPanelSelection () { + var app = this; + + // Setup panel highlighting on check + $('body').on('change', '.check-all-slave', function (event) { + var checked = $(event.target).prop('checked'); + if (checked) { + $(this).closest('.panel-item').addClass('panel-highlighted'); + } else { + $(this).closest('.panel-item').removeClass('panel-highlighted'); + } + }); + + $('body').on('click', '.panel-item', function (event) { + var $this = $(this); + var targetSrc = $(event.target).prop('src'); + var targetHref = $(event.target).prop('href'); + var targetIsButton = event.target.tagName === 'BUTTON'; + var lastChecked = null; + + if ((targetSrc === undefined) && (targetHref === undefined) && (targetIsButton === false)) { + var $checkbox = $this.find('.check-all-slave'); + var checked = $checkbox.prop('checked'); + + if (checked) { + $checkbox.prop('checked', ''); + $checkbox.trigger('change'); + } else { + $checkbox.prop('checked', 'checked'); + $checkbox.trigger('change'); + } + + if(!app.lastChecked) { + app.lastChecked = $checkbox; + } + + if (event.shiftKey) { + var $checkBoxes = $('.check-all-slave'); + + var start = $checkBoxes.index($checkbox); + var end = $checkBoxes.index(app.lastChecked); + + $checkBoxes.slice( + Math.min(start, end), Math.max(start, end) + 1 + ).prop('checked', app.lastChecked.prop('checked')).trigger('change'); + } + app.lastChecked = $checkbox; + window.getSelection().removeAllRanges(); + } + }); + } + setupScrollView () { $('.scrollable').scrollview(); } diff --git a/mayan/apps/appearance/templates/appearance/generic_list_items_subtemplate.html b/mayan/apps/appearance/templates/appearance/generic_list_items_subtemplate.html index e0c4166cef..63ddc71018 100644 --- a/mayan/apps/appearance/templates/appearance/generic_list_items_subtemplate.html +++ b/mayan/apps/appearance/templates/appearance/generic_list_items_subtemplate.html @@ -23,26 +23,20 @@ {% endif %}
+
-
-
-
- {% if object_list %} - {% if not hide_multi_item_actions %} - {% get_multi_item_links_form object_list %} - {% endif %} - {% if multi_item_actions %} -
-   - {{ multi_item_form }} -
- {% endif %} - {% endif %} -
-
-
{% if object_list %} + {% if not hide_multi_item_actions %} + {% navigation_resolve_menu name='multi item' sort_results=True source=object_list.0 as links_multi_menus_results %} + {% endif %} + {% endif %} + +
+ {% include 'appearance/list_toolbar.html' %} +
+ + {% if links_multi_menus_results %}
{% endif %} @@ -54,8 +48,8 @@
- {% if not hide_columns %} {% navigation_get_source_columns source=object exclude_identifier=True as source_columns %} {% for column in source_columns %} diff --git a/mayan/apps/appearance/templates/appearance/generic_list_subtemplate.html b/mayan/apps/appearance/templates/appearance/generic_list_subtemplate.html index d0aa3d6b88..e3e03e4d5a 100644 --- a/mayan/apps/appearance/templates/appearance/generic_list_subtemplate.html +++ b/mayan/apps/appearance/templates/appearance/generic_list_subtemplate.html @@ -25,30 +25,27 @@
+ {% if object_list %} + {% if not hide_multi_item_actions %} + {% navigation_resolve_menu name='multi item' sort_results=True source=object_list.0 as links_multi_menus_results %} + {% endif %} + {% endif %} +
-
-
- {% if object_list %} - {% if not hide_multi_item_actions %} - {% get_multi_item_links_form object_list %} - {% endif %} - {% if multi_item_actions %} -
- {{ multi_item_form }} -
- {% endif %} - {% endif %} -
-
+ {% include 'appearance/list_toolbar.html' %}
+ {% if links_multi_menus_results %} +
+ {% endif %} +
{% if not hide_header %} - {% if multi_item_actions %} - + {% if links_multi_menus_results %} + {% endif %} {% if not hide_object %} @@ -99,9 +96,9 @@ {% for object in object_list %} - {% if multi_item_actions %} + {% if links_multi_menus_results %} {% endif %} diff --git a/mayan/apps/appearance/templates/appearance/list_toolbar.html b/mayan/apps/appearance/templates/appearance/list_toolbar.html new file mode 100644 index 0000000000..e94eedb3f7 --- /dev/null +++ b/mayan/apps/appearance/templates/appearance/list_toolbar.html @@ -0,0 +1,49 @@ +{% load i18n %} + +{% load common_tags %} +{% load navigation_tags %} + +
+ +
+ + +{% if links_multi_menus_results %} +

{% trans 'Select items to activate bulk actions. Use Shift + click to select many.' %}

+ + +
+{% endif %} diff --git a/mayan/apps/common/urls.py b/mayan/apps/common/urls.py index 13fd7e3fac..205c90b066 100644 --- a/mayan/apps/common/urls.py +++ b/mayan/apps/common/urls.py @@ -10,7 +10,7 @@ from .views import ( AboutView, CurrentUserLocaleProfileDetailsView, CurrentUserLocaleProfileEditView, FaviconRedirectView, HomeView, LicenseView, ObjectErrorLogEntryListClearView, ObjectErrorLogEntryListView, - RootView, SetupListView, ToolsListView, multi_object_action_view + RootView, SetupListView, ToolsListView ) urlpatterns = [ @@ -18,10 +18,6 @@ urlpatterns = [ url(regex=r'^home/$', view=HomeView.as_view(), name='home'), url(regex=r'^about/$', view=AboutView.as_view(), name='about_view'), url(regex=r'^license/$', view=LicenseView.as_view(), name='license_view'), - url( - regex=r'^object/multiple/action/$', view=multi_object_action_view, - name='multi_object_action_view' - ), url(regex=r'^setup/$', view=SetupListView.as_view(), name='setup_list'), url(regex=r'^tools/$', view=ToolsListView.as_view(), name='tools_list'), url( diff --git a/mayan/apps/common/views.py b/mayan/apps/common/views.py index 30f16cc0f4..b97cccf9e4 100644 --- a/mayan/apps/common/views.py +++ b/mayan/apps/common/views.py @@ -220,67 +220,3 @@ class ToolsListView(SimpleView): 'These modules are used to do system maintenance.' ) } - - -def multi_object_action_view(request): - """ - Proxy view called first when using a multi object action, which - then redirects to the appropriate specialized view - """ - next = request.POST.get( - 'next', request.GET.get( - 'next', request.META.get( - 'HTTP_REFERER', reverse(setting_home_view.value) - ) - ) - ) - - action = request.GET.get('action', None) - id_list = ','.join( - [key[3:] for key in request.GET.keys() if key.startswith('pk_')] - ) - items_property_list = [ - (key[11:]) for key in request.GET.keys() if key.startswith('properties_') - ] - - if not action: - messages.error( - message=_('No action selected.'), request=request - ) - return HttpResponseRedirect( - redirect_to=request.META.get( - 'HTTP_REFERER', reverse(setting_home_view.value) - ) - ) - - if not id_list and not items_property_list: - messages.error( - message=_('Must select at least one item.'), - request=request - ) - return HttpResponseRedirect( - redirect_to=request.META.get( - 'HTTP_REFERER', reverse(setting_home_view.value) - ) - ) - - # Separate redirects to keep backwards compatibility with older - # functions that don't expect a properties_list parameter - if items_property_list: - return HttpResponseRedirect( - redirect_to='%s?%s' % ( - action, - urlencode( - { - 'items_property_list': dumps(items_property_list), - 'next': next - } - ) - ) - ) - else: - return HttpResponseRedirect( - redirect_to='%s?%s' % ( - action, urlencode({'id_list': id_list, 'next': next}) - ) - )
- +