From 9b0dcbcb80de075d7fc51b9bf052662ede16cd04 Mon Sep 17 00:00:00 2001 From: bellord13 Date: Tue, 5 Oct 2021 23:13:01 +0300 Subject: [PATCH] fix --- assets/UserActionManager/UserActionManager.js | 129 +++++++++ assets/collection/collection.js | 253 ++++++++++-------- assets/menu/menu.js | 16 +- tests/kit.Collection.php | 36 +++ 4 files changed, 317 insertions(+), 117 deletions(-) diff --git a/assets/UserActionManager/UserActionManager.js b/assets/UserActionManager/UserActionManager.js index b76d39d..d42ab97 100644 --- a/assets/UserActionManager/UserActionManager.js +++ b/assets/UserActionManager/UserActionManager.js @@ -4,12 +4,141 @@ */ kit.PluginManager.register('UserActionManager',function(module, exports, require, global) { + var Collection = require('collection'); + var actionList = ['click', 'hover']; var UserAction = function () { + this.parentActionHandler = this.parentAction.bind(this); + this.documentListenerHandler = this.documentListener.bind(this); + this.nodeActionHandler = this.nodeAction.bind(this); + + this.clickHandlerCollection = new Collection([]); + this.dblclickHandlerCollection = new Collection([]); + this.mouseoverHandlerCollection = new Collection([]); + this.mouseoutHandlerCollection = new Collection([]); + + this.handleEvent = function(event) { + switch(event.type) { + case 'mouseover': + this.mouseoverHandlerCollection.each(function (event, ) { + item + }); + break; + case 'mouseout': + this.options.hover(event, _thisMenuItem, MenuList[_thisMenuItem.parentId]); + break; + case 'click': + this.options.click(event, _thisMenuItem, MenuList[_thisMenuItem.parentId]); + break; + case 'dblclick': + this.options.dblclick(event, _thisMenuItem, MenuList[_thisMenuItem.parentId]); + break; + } + }; }; var proto = UserAction.prototype; + proto.documentListener = function(event) { + + if(this.options.eventType === 'click') { + if (this.needHideByParent(event.target)) { + this.toggle(); + } + } + }; + proto.parentAction = function (event) { + event.stopPropagation(); + // event.stopImmediatePropagation(); + switch (event.type) { + case 'mouseout': + if (this.needHideByParent(event.relatedTarget)) { + this.hideNodeDeferred(); + } + break; + case 'mouseover': + this.showNode(); + break; + case 'click': + this.toggle(); + break; + } + }; + proto.nodeAction = function (event) { + event.stopPropagation(); + // event.stopImmediatePropagation(); + switch (event.type) { + case 'mouseout': + break; + case 'mouseover': + break; + case 'mouseleave': + if(this.options.eventType === 'hover') { + this.hideNodeDeferred(); + } + break; + case 'mouseenter': + this.deferredHideCancel(); + break; + } + }; + + proto.addDocumentEventListener = function() { + document.addEventListener('click', this.documentListenerHandler, false); + }; + proto.removeDocumentEventListener = function() { + document.removeEventListener('click', this.documentListenerHandler, false); + }; + proto.removeParentEventListener = function() { + // console.log('Menu: removeParentEventListener'); + if(this.node instanceof Element) { + this.node.classList.remove('active'); + this.node.removeEventListener('click', this.parentActionHandler, false); + this.node.removeEventListener('mouseover', this.parentActionHandler, false); + this.node.removeEventListener('mouseout', this.parentActionHandler, false); + } + }; + proto.addParentEventListener = function() { + if(this.node instanceof Element) { + if(this.options.eventType === 'hover') { + this.node.addEventListener('mouseover', this.parentActionHandler, false); + this.node.addEventListener('mouseout', this.parentActionHandler, false); + } + if(this.options.eventType === 'click') { + this.node.addEventListener(this.options.eventType, this.parentActionHandler, false); + } + } + }; + proto.addNodeEventListener = function() { + if(!this.node) { + return; + } + + this.node.addEventListener('mouseenter', this.nodeActionHandler, false); + this.node.addEventListener('mouseleave', this.nodeActionHandler, false); + }; + proto.removeNodeEventListener = function() { + if(!this.node) { + return; + } + + this.node.removeEventListener('mouseenter', this.nodeActionHandler, false); + this.node.removeEventListener('mouseleave', this.nodeActionHandler, false); + }; + proto.active = function(){ + this.node.addEventListener('mouseover', this, false); + this.node.addEventListener('click', this, false); + this.node.addEventListener('dblclick', this, false); + }; + proto.clear = function(){ + this.node.removeEventListener('mouseover', this, false); + this.node.removeEventListener('click', this, false); + this.node.removeEventListener('dblclick', this, false); + }; + proto.destroy = function(){ + + }; + proto.setAction = function (action) { if(actionList.indexOf(action) === -1) { action = 'click'; diff --git a/assets/collection/collection.js b/assets/collection/collection.js index 705723f..0ee0465 100644 --- a/assets/collection/collection.js +++ b/assets/collection/collection.js @@ -1,9 +1,9 @@ /** @module collection */ kit.PluginManager.register('collection',function(module, exports, require, global) { - function valueEx(value, item, key) { + function valueEx(value, item, key, arr) { if(typeof value === 'function') { - return value(item, key); + return value(item, key, arr); } return value; } @@ -19,149 +19,190 @@ kit.PluginManager.register('collection',function(module, exports, require, globa } while (idStr.length < length); return (idStr); } - - - var ArrayCollection = function (data){ + function empty(val){ + return arguments.length === 0 || + val === undefined || + val === null || + Number.isNaN(val) === true || + val === '' || + val === 0 || + val === false; + } + function filter(value, key, arr) { + return !empty(value); + } + function getSimilarInstance(type) { + if(type === 'object') { + return new Collection({}); + } + return new Collection([]); + } + /** + * @memberof kitCore + * @instance + */ + var Collection = function (data) { this.data = data; + if(data instanceof NodeList) { + this.type = 'NodeList'; + } + else if(Array.isArray(data)) { + this.type = 'Array'; + } + else if(typeof data === 'object') { + this.type = 'object'; + } + else { + this.type = 'Array'; + this.data = [data]; + this.type = undefined; + console.warn('collection: not support data' + typeof data); + } }; - ArrayCollection.prototype.all = function () { + + Collection.prototype.all = function () { return this.data; }; - ArrayCollection.prototype.put = function (key, value) { + /** + * @param key + * @param value + * @return {kitCore.Collection} + */ + Collection.prototype.set = Collection.prototype.put = function (key, value) { this.data[key] = value; return this; }; - ArrayCollection.prototype.set = ArrayCollection.prototype.put; - ArrayCollection.prototype.push = function (value) { - this.data.push(value); + /** + * @param value + * @return {kitCore.Collection} + */ + Collection.prototype.push = function (value) { + if(this.type === 'Array') { + this.data.push(value); + return this; + } + this.data[uniqueId(8)] = value; + return this; }; - ArrayCollection.prototype.get = function (key, defValue = undefined) { + Collection.prototype.get = function (key, defValue = undefined) { if(this.data.hasOwnProperty(key)) { return this.data[key]; } return valueEx(defValue, this.data[key], key); }; - ArrayCollection.prototype.has = function (key) { + Collection.prototype.has = function (key) { return this.data.hasOwnProperty(key); }; - ArrayCollection.prototype.count = function () { + Collection.prototype.count = function () { return Object.keys(this.data).length; }; - ArrayCollection.prototype.isEmpty = function () { + Collection.prototype.isEmpty = function () { return this.count() === 0; }; - ArrayCollection.prototype.map = function (callback) { + /** + * @param callback + * @return {kitCore.Collection} + */ + Collection.prototype.map = function (callback) { + var res = getSimilarInstance(this.type); for (var key of Object.keys(this.data)) { - this.data[key] = callback(this.data[key], key, this.data); + res.put(key, callback(this.data[key], key, this.data)); } - return this; + return res; }; - ArrayCollection.prototype.each = function (callback) { - var BreakException = {}; + /** + * @param callback + * @return {kitCore.Collection} + */ + Collection.prototype.each = function (callback = true) { + var BreakException = {}, keys, i, key; try { - for (var key of Object.keys(this.data)) { - if(callback(this.data[key], key, this.data) === false) { - throw BreakException; + keys = Object.keys(this.data); + if(keys.length) + for (i = 0; i < keys.length; i++) { + key = keys[i]; + if(valueEx(callback, this.data[key], key, this.data) === false) { + throw BreakException; + } } - } } catch (e) { if (e !== BreakException) throw e; } return this; }; - - - var ObjectCollection = function (data){ - this.data = data; - }; - ObjectCollection.prototype.all = ArrayCollection.prototype.all; - ObjectCollection.prototype.put = ArrayCollection.prototype.put; - ObjectCollection.prototype.set = ArrayCollection.prototype.put; - ObjectCollection.prototype.push = function (value) { - this.data[uniqueId(8)] = value; - return this; - }; - ObjectCollection.prototype.get = ArrayCollection.prototype.get; - ObjectCollection.prototype.has = ArrayCollection.prototype.has; - ObjectCollection.prototype.count = ArrayCollection.prototype.count; - ObjectCollection.prototype.isEmpty = ArrayCollection.prototype.isEmpty; - ObjectCollection.prototype.map = ArrayCollection.prototype.map; - ObjectCollection.prototype.each = ArrayCollection.prototype.each; - - - var NodeCollection = function (data){ - this.data = data; - }; - NodeCollection.prototype.all = ArrayCollection.prototype.all; - NodeCollection.prototype.put = ArrayCollection.prototype.put; - NodeCollection.prototype.set = ArrayCollection.prototype.put; - NodeCollection.prototype.push = ArrayCollection.prototype.push; - NodeCollection.prototype.get = ArrayCollection.prototype.get; - NodeCollection.prototype.has = ArrayCollection.prototype.has; - NodeCollection.prototype.count = ArrayCollection.prototype.count; - NodeCollection.prototype.isEmpty = ArrayCollection.prototype.isEmpty; - NodeCollection.prototype.map = ArrayCollection.prototype.map; - NodeCollection.prototype.each = ArrayCollection.prototype.each; - - function collectionCall(method, args) { - if(this.__driver.__proto__.hasOwnProperty(method)) { - var r = this.__driver[method].apply(this.__driver, args); - return r === this.__driver ? this : r; - } - return this; - } /** - * @extends ArrayCollection - * @memberof kitCore - * @instance + * @param callback + * @return {kitCore.Collection} */ - var Collection = function (data) { - if(data instanceof NodeList) { - this.__driver = new NodeCollection(data); - } - else if(Array.isArray(data)) { - this.__driver = new ArrayCollection(data); - } - else if(typeof data === 'object') { - this.__driver = new ObjectCollection(data); - } - else { - console.warn('collection: not support data', data); + Collection.prototype.eachReverse = function (callback = true) { + var BreakException = {}, keys, i, key; + try { + keys = Object.keys(this.data); + if(keys.length) + for (i = keys.length - 1; i >= 0; i--) { + key = keys[i]; + if(valueEx(callback, this.data[key], key, this.data) === false) { + throw BreakException; + } + } + } catch (e) { + if (e !== BreakException) throw e; } + return this; }; - Collection.prototype.all = function () { - return collectionCall.call(this, 'all', arguments); + /** + * @param callback + * @return {kitCore.Collection} + */ + Collection.prototype.filter = function (callback = filter) { + var res = getSimilarInstance(this.type); + this.each(function (value, key, arr) { + if(callback(value, key, arr)) { + res.put(key, value); + } + }); + return res; }; - Collection.prototype.put = function (key, value) { - return collectionCall.call(this, 'put', arguments); + Collection.prototype.every = function (callback) { + var res = true; + this.each(function (value, key, arr) { + res = res && !!callback(value, key, arr); + }); + return res; }; - Collection.prototype.set = function (key, value) { - return collectionCall.call(this, 'set', arguments); + Collection.prototype.first = function (callback = true) { + var res = undefined; + this.each(function (value, key, arr) { + if(valueEx(callback, value, key, arr)) { + res = value; + return false; + } + }); + return res; }; - Collection.prototype.push = function (value) { - return collectionCall.call(this, 'push', arguments); + Collection.prototype.last = function (callback = true) { + var res = undefined; + this.eachReverse(function (value, key, arr) { + if(valueEx(callback, value, key, arr)) { + res = value; + return false; + } + }); + return res; }; - Collection.prototype.get = function (key, defValue = undefined) { - return collectionCall.call(this, 'get', arguments); + /** + * @return {kitCore.Collection} + */ + Collection.prototype.keys = function () { + return new Collection(Object.keys(this.data)); }; - Collection.prototype.has = function (key) { - return collectionCall.call(this, 'has', arguments); + /** + * @return {kitCore.Collection} + */ + Collection.prototype.dump = Collection.prototype.dd = function () { + console.log('Collection', this.data); + return this; }; - Collection.prototype.count = function () { - return collectionCall.call(this, 'count', arguments); - }; - Collection.prototype.isEmpty = function () { - return collectionCall.call(this, 'isEmpty', arguments); - }; - Collection.prototype.map = function (callback) { - return collectionCall.call(this, 'map', arguments); - }; - Collection.prototype.each = function (callback) { - return collectionCall.call(this, 'each', arguments); - }; - - - return module.exports = Collection; }); diff --git a/assets/menu/menu.js b/assets/menu/menu.js index bbf9c02..ddbec08 100644 --- a/assets/menu/menu.js +++ b/assets/menu/menu.js @@ -206,17 +206,10 @@ __PluginManager__.register('menu',function(module, exports, require) { * @return {Menu} | null */ Menu.prototype.getParentMenu = function() { - if(this.getParent() && this.getParent().kitMenuItem) { - return this.getParent().kitMenuItem.getMenu(); + var p = this.getParent(); + if(p instanceof Element && p.hasOwnProperty('kit') && p.kit.menuItem instanceof MenuItemClass) { + return p.kit.menuItem.getMenu(); } - return undefined; - if( - this.getParent() && (this.getParent() instanceof Element) && - this.getParent().hasOwnProperty('kitMenuItem') && (this.getParent().kitMenuItem instanceof MenuItemClass) - ) { - return this.getParent().kitMenuItem.getMenu(); - } - return undefined; }; Menu.prototype.getParentMenuNode = function() { var parentMenu = this.getParentMenu(), @@ -586,7 +579,8 @@ __PluginManager__.register('menu',function(module, exports, require) { this.node = document.createElement('a'); this.node.style.position = 'relative'; this.node.dataset.parentId = this.parentId; - this.node.kitMenuItem = this; + this.node.kit = this.node.kit || {}; + this.node.kit.menuItem = this; }; /** diff --git a/tests/kit.Collection.php b/tests/kit.Collection.php index 47ec277..f637f6f 100644 --- a/tests/kit.Collection.php +++ b/tests/kit.Collection.php @@ -71,6 +71,42 @@ kit.ready(['collection'], function () { } testFunction(1, 2, 3, 4, 5, 6, 7, 8); + + + + collection = new kit.Collection([1, 2, 3, '', 0, NaN, undefined, null, false, true]); + assertSame(collection.filter().count(), 4, 'filter'); + + collection = new kit.Collection([4, 5, 6]); + assertSame(collection.every(function (item) { + return item > 2; + }), true, 'every'); + assertSame(collection.every(function (item) { + return item > 5; + }), false, 'every'); + assertSame(collection.every(function (item) { + return item < 1; + }), false, 'every'); + + + collection = new kit.Collection([10, 20, 30]); + assertSame(collection.first(), 10, 'first'); + assertSame(collection.first(function (item) { + return item > 15; + }), 20, 'first'); + assertSame(collection.first(function (item) { + return item < 0; + }), undefined, 'first'); + + assertSame(collection.last(), 30, 'first'); + assertSame(collection.last(function (item) { + return item < 25; + }), 20, 'first'); + assertSame(collection.last(function (item) { + return item < 0; + }), undefined, 'first'); + + assertSame(collection.keys().count(), 3, 'keys'); });