import $ from 'jquery' import XE from 'xe' // TODO:: mouseover, const Keys = { ENTER: 13, TAB: 9, BACKSPACE: 8, UP_ARROW: 38, DOWN_ARROW: 40, ESCAPE: 27 } class Permission { constructor ({ $wrapper, key, userSearchUrl, groupSearchUrl, permission, type, vgroupAll }) { this.$wrapper = $wrapper this.key = key this.userSearchUrl = userSearchUrl this.groupSearchUrl = groupSearchUrl this.permission = permission this.type = type this.vgroupAll = vgroupAll this.query = '' this.suggestion = [] this.placeholder = XE.Lang.trans('xe::explainIncludeUserOrGroup') this.selectedIndex = '' this.includeSelectedIndex = -1 this.excludeSelectedIndex = -1 this.MIN_QUERY_LENGTH = 2 } bindEvents () { var _this = this this.$wrapper.on('change', '.chkModeAble', function (e) { var $target = $(e.target) var checked = $target.is(':checked') if (checked) { _this.$wrapper.find('input:not(.chkModeAble)').prop('disabled', true) } else { _this.$wrapper.find('input:not(.chkModeAble)').prop('disabled', false) } }) this.$wrapper.on('keydown', '.inputUserGroup', function (e) { var query = e.target.value.trim() var $this = $(this) var keyCode = e.keyCode var $ul = $this.parent().find('.ReactTags__suggestions ul') var dataInput = $this.data('input') // include, exclude if (query.length >= _this.MIN_QUERY_LENGTH) { if ($ul.length > 0) { var index = parseInt($this.data('index'), 10) var focusedIndex = 0 switch (keyCode) { case Keys.UP_ARROW : if (index == 0) { focusedIndex = $ul.find('li').length - 1 } else { focusedIndex = (index - 1) } $this.data('index', focusedIndex) $ul.find('li').eq(focusedIndex).addClass('active').siblings().removeClass('active') break case Keys.DOWN_ARROW : if (index == $ul.find('li').length - 1) { focusedIndex = 0 } else { focusedIndex = index + 1 } $this.data('index', focusedIndex) $ul.find('li').eq(focusedIndex).addClass('active').siblings().removeClass('active') break case Keys.ENTER : case Keys.TAB : e.preventDefault() if ($ul.find('li.active').length > 0) { var tag = $ul.find('li.active').data('tag') var name = '' var pType = '' var prefix = '' // user if ($ul.data('target') === 'user') { // include if (dataInput === 'include') { name = _this.type + 'User' pType = 'user' prefix = '@' // exclude } else { name = _this.type + 'Except' pType = 'except' prefix = '@' } // group } else { name = _this.type + 'Group' pType = 'group' prefix = '%' } var pTypes = _this.permission[pType] var bSameWord = false if (pTypes.length > 0) { pTypes.forEach(function (type, i) { if (type.id === tag.id) { bSameWord = true } }) if (!bSameWord) { _this.permission[pType].push(tag) } } else { _this.permission[pType].push(tag) } var ids = _this.permission[pType].map(function (tag) { return tag.id }) if (!bSameWord) { $ul.closest('.ReactTags__tags').find('[name=' + name + ']').val(ids.join().trim()) $ul.closest('.ReactTags__tags').find('.' + pType + 'Wrap') .append(`${prefix + (tag.display_name || tag.name)}x`) } $ul.remove() $this.val('').data('index', -1).focus() } e.preventDefault() // prevent tab break case Keys.ESCAPE : _this[dataInput + 'SelectedIndex'] = 0 $ul.parent().empty() $this.focus() break } } } else { if (Keys.BACKSPACE === keyCode) { var $tag = $this.closest('.ReactTags__tags').find('.ReactTags__selected span') if (!query && $tag.length > 0) { _this.removeTag($tag.eq($tag.length - 1)) } } } }) this.$wrapper.find('.ReactTags__suggestions').on('mouseenter', 'li', function () { var $this = $(this) $this.addClass('active').siblings().removeClass('active') }) this.$wrapper.find('.ReactTags__suggestions').on('click', 'li', function () { var $this = $(this) var tag = $this.data('tag') var $ul = $this.closest('ul') var $input = $this.closest('.ReactTags__tagInput').find('input:text') var dataInput = $input.data('input') var name = '' var pType = '' var prefix = '' if ($ul.data('target') === 'user') { // include if (dataInput === 'include') { name = _this.type + 'User' pType = 'user' prefix = '@' // exclude } else { name = _this.type + 'Except' pType = 'except' prefix = '@' } // group } else { name = _this.type + 'Group' pType = 'group' prefix = '%' } var pTypes = _this.permission[pType] var bSameWord = false if (pTypes.length > 0) { pTypes.forEach(function (type, i) { if (type.id === tag.id) { bSameWord = true } }) if (!bSameWord) { _this.permission[pType].push(tag) } } else { _this.permission[pType].push(tag) } var ids = _this.permission[pType].map(function (tag) { return tag.id }) if (!bSameWord) { $ul.closest('.ReactTags__tags').find('[name=' + name + ']').val(ids.join().trim()) $ul.closest('.ReactTags__tags').find('.' + pType + 'Wrap') .append(`${prefix + (tag.display_name || tag.name)}x`) } $ul.remove() $input.val('').data('index', -1).focus() }) this.$wrapper.on('keyup', '.inputUserGroup', function (e) { var query = e.target.value.trim() var $this = $(this) var keyCode = e.keyCode if (query.length >= _this.MIN_QUERY_LENGTH) { if ([Keys.ENTER, Keys.TAB, Keys.UP_ARROW, Keys.DOWN_ARROW, Keys.ESCAPE, 37, 39].indexOf(keyCode) == -1) { var temp = '' temp += `` $this.parent().find('.ReactTags__suggestions').html(temp) var identifier = query.substr(0, 1) switch (identifier) { case '@': query = query.substr(1, query.length) _this.searchUser($this, query) break case '%': query = query.substr(1, query.length) _this.searchGroup($this, query) break default : break } } } else { $this.parent().find('.ReactTags__suggestions').empty() } }) this.$wrapper.on('click', '.btnRemoveTag', function (e) { e.preventDefault() _this.removeTag($(this).closest('span')) }) } makeIt (item, query) { var escapedRegex = query.trim().replace(/[-\\^$*+?.()|[\]{}]/g, '\\$&') var r = RegExp(escapedRegex, 'gi') var itemName = item.display_name || item.name return itemName.replace(r, '$&') } removeTag ($target) { var _this = this var pType = $target.closest('.ReactTags__selected').data('ptype') var id = $target.data('id') var name = '' switch (pType) { case 'user' : name = _this.type + 'User' break case 'except' : name = _this.type + 'Except' break case 'group' : name = _this.type + 'Group' break } var pTypes = _this.permission[pType] pTypes.forEach(function (type, i) { if (type.id !== id) { _this.permission[pType].splice(i, 1)// .push(tag); } }) var ids = _this.permission[pType].map(function (tag) { return tag.id }) $target.closest('.ReactTags__tags').find('[name=' + name + ']').val(ids.join().trim()) $target.remove() } searchUser ($input, keyword) { var _this = this var searchUserUrl = _this.userSearchUrl XE.ajax({ url: searchUserUrl + '/' + keyword, method: 'get', dataType: 'json', cache: false, success: function (data) { if (data.length > 0) { var temp = '' temp += `` $input.parent().find('.ReactTags__suggestions').html(temp) } else { $input.parent().find('.ReactTags__suggestions').empty() } }, error: function (xhr, status, err) { } }) } searchGroup ($input, keyword) { var _this = this var searchGroupUrl = _this.groupSearchUrl XE.ajax({ url: searchGroupUrl + '/' + keyword, method: 'get', dataType: 'json', cache: false, success: function (data) { // TODO:: view renderin if (data.length > 0) { var temp = '' temp += `` $input.parent().find('.ReactTags__suggestions').html(temp) } else { $input.parent().find('.ReactTags__suggestions').empty() } }, error: function (xhr, status, err) {} }) } render () { var _this = this var mode = this.permission.mode var rating = this.permission.rating var modeEnable = false var permissionTypes = [ { value: 'super', name: XE.Lang.trans('xe::userRatingAdministrator') }, { value: 'manager', name: XE.Lang.trans('xe::userRatingManager') }, { value: 'user', name: XE.Lang.trans('xe::user') }, { value: 'guest', name: XE.Lang.trans('xe::guest') } ] var disabled = false if (mode === 'manual' || mode === 'inherit') { modeEnable = true if (mode !== 'manual') { disabled = true } } var includeGroups = this.permission.group.map(function (group) { return group.id }) var includeUsers = this.permission.user.map(function (user) { return user.id }) var excludeUsers = this.permission.except.map(function (user) { return user.id }) var temp = '' temp += `
` if (modeEnable) { var checked = (mode === 'inherit') ? 'checked="checked"' : '' temp += `
` temp += `
` temp += `` temp += `
` temp += `
` } temp += `
` temp += `` temp += '
' permissionTypes.forEach(function (permissionType) { var checked = (permissionType.value == rating) ? 'checked' : '' temp += `` }) temp += `
` temp += `
` temp += `
` temp += `` temp += `
` temp += `
` this.permission.group.forEach(function (g) { var tag = g var label = '%' + (tag.display_name || tag.name) temp += `${label}x` }) temp += '
' temp += '
' this.permission.user.forEach(function (tag) { var label = '@' + (tag.display_name || tag.name) temp += `${label}x` }) temp += `
` temp += `
` temp += `` // TODO:: PermissionInclude handleKeyDown temp += `
` temp += `
` // ReactTags__tagInput temp += `` temp += `` temp += `
` // ReactTags__tags temp += `
`// form-group if (this.vgroupAll.length >= 1) { temp += `
` temp += `` temp += _this.vgroupAll.map(function (data) { var checked = false var inArray = function (val, arr) { for (var i = 0; i < arr.length; i++) { if (arr[i] == val) { return i } } return -1 } if (inArray(data.id, this.permission.vgroup) != -1) { checked = true } return `` }) temp += '
' } temp += `
` temp += `` temp += `
` temp += `
` this.permission.except.forEach(function (tag) { var label = tag.display_name || tag.name label = '@' + label temp += `${label}x` }) temp += `
` temp += `
` temp += `` // TODO:: PermissionExclude handleKeyDown temp += `
` temp += `
` // ReactTags__tagInput temp += `` temp += `
` // ReactTags__tags temp += `
`// form-group temp += `
` this.$wrapper.html(temp) } } $('.__xe__uiobject_permission').each(function (i) { var $this = $(this) var permission = $this.data('data') var key = $this.data('key') var type = $this.data('type') var userSearchUrl = $this.data('userUrl') var groupSearchUrl = $this.data('groupUrl') var vgroupAll = $this.data('vgroupAll') var p = new Permission({ $wrapper: $this, key, userSearchUrl, groupSearchUrl, permission, type, vgroupAll }) p.render() p.bindEvents() })