From 15da2fe2573699c0ecd72a40da92f5ff40882b2e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?J=C3=BCrg=20Lehni?= Date: Sun, 29 May 2011 19:54:43 +0100 Subject: [PATCH] Implement Item#isAbove / #isBelow and define tests for it. --- src/item/Item.js | 36 ++++++++++++++++++++++++++++++-- src/load.js | 7 +++++++ test/tests/Item_Order.js | 45 ++++++++++++++++++++++++++++++++++++++++ 3 files changed, 86 insertions(+), 2 deletions(-) create mode 100644 test/tests/Item_Order.js diff --git a/src/item/Item.js b/src/item/Item.js index d9911f06..f498672b 100644 --- a/src/item/Item.js +++ b/src/item/Item.js @@ -607,6 +607,32 @@ var Item = this.Item = Base.extend({ */ // TODO: isValid / checkValid + /** + * Returns -1 if 'this' is above 'item', 1 if below, 0 if their order is not + * defined in such a way, e.g. if one is a descendant of the other. + */ + _getOrder: function(item) { + // Private method that prodces a list of anchestors, starting with the + // root and the actual element as the last entry. + function getList(item) { + var list = []; + do { + list.unshift(item); + } while (item = item._parent) + return list; + } + var list1 = getList(this), + list2 = getList(item); + for (var i = 0, l = Math.min(list1.length, list2.length); i < l; i++) { + if (list1[i] != list2[i]) { + // Found the position in the parents list where the two start + // to differ. Look at who's above who. + return list1[i]._index < list2[i]._index ? 1 : -1; + } + } + return 0; + }, + /** * Checks if this item is above the specified item in the stacking order * of the project. @@ -614,7 +640,9 @@ var Item = this.Item = Base.extend({ * @param {Item} item The item to check against * @return {boolean} {@true if it is above the specified item} */ - // TODO: isAbove + isAbove: function(item) { + return this._getOrder(item) == -1; + }, /** * Checks if the item is below the specified item in the stacking order of @@ -623,7 +651,9 @@ var Item = this.Item = Base.extend({ * @param {Item} item The item to check against * @return {boolean} {@true if it is below the specified item} */ - // TODO: isBelow + isBelow: function(item) { + return this._getOrder(item) == 1; + }, /** * {@grouptitle Hierarchy Tests} @@ -652,6 +682,7 @@ var Item = this.Item = Base.extend({ * @param {Item} item The item to check against * @return {boolean} {@true if it is inside the specified item} */ + // TODO: Consider naming this isInside? isDescendant: function(item) { var parent = this; while (parent = parent._parent) { @@ -668,6 +699,7 @@ var Item = this.Item = Base.extend({ * @return {boolean} {@true if the item is an ancestor of the specified * item} */ + // TODO: Consider naming this contains? isAncestor: function(item) { return item ? item.isDescendant(this) : false; }, diff --git a/src/load.js b/src/load.js index b14b32e6..34433ca2 100644 --- a/src/load.js +++ b/src/load.js @@ -93,13 +93,19 @@ if (window.tests) { 'test/tests/Point.js', 'test/tests/Size.js', 'test/tests/Rectangle.js', + 'test/tests/Color.js', + 'test/tests/Project.js', + 'test/tests/Item.js', 'test/tests/Item_Cloning.js', + 'test/tests/Item_Order.js', + 'test/tests/Layer.js', 'test/tests/Group.js', 'test/tests/Segment.js', + 'test/tests/Path.js', 'test/tests/PathStyle.js', 'test/tests/Path_Shapes.js', @@ -108,6 +114,7 @@ if (window.tests) { 'test/tests/Path_Bounds.js', 'test/tests/Path_Length.js', 'test/tests/CompoundPath.js', + 'test/tests/PlacedSymbol.js' ); } diff --git a/test/tests/Item_Order.js b/test/tests/Item_Order.js new file mode 100644 index 00000000..cc0ee9e0 --- /dev/null +++ b/test/tests/Item_Order.js @@ -0,0 +1,45 @@ +test('Item Order', function() { + var line = new Path(); + line.add([0, 0], [100, 100]); + line.name = 'line'; + + var circle = new Path.Circle([50, 50], 50); + circle.name = 'circle'; + + window.console.log(circle._getOrder(line), circle.isAbove(line)); + + var group = new Group([circle]); + group.name = 'group'; + + equals(function() { + return circle.isAbove(line); + }, true); + equals(function() { + return line.isBelow(circle); + }, true); + + equals(function() { + return group.isAbove(line); + }, true); + equals(function() { + return line.isBelow(group); + }, true); + + + equals(function() { + return group.isAncestor(circle); + }, true); + + equals(function() { + return circle.isDescendant(group); + }, true); + + + equals(function() { + return group.isAbove(circle); + }, false); + + equals(function() { + return group.isBelow(circle); + }, false); +});