From 2bd246e2eaf83e43baa064d0d52ba779c7f99c92 Mon Sep 17 00:00:00 2001 From: Dan Stillman Date: Mon, 25 May 2015 21:22:43 -0400 Subject: [PATCH] Fixes #728, Tag selector refreshing --- .../content/zotero/bindings/tagselector.xml | 35 ++++- .../zotero/xpcom/collectionTreeView.js | 25 +-- chrome/content/zotero/xpcom/itemTreeView.js | 22 ++- chrome/content/zotero/xpcom/notifier.js | 88 +++++++---- chrome/content/zotero/zoteroPane.js | 2 +- test/tests/collectionTreeViewTest.js | 3 +- test/tests/tagSelectorTest.js | 145 ++++++++++++++++++ 7 files changed, 268 insertions(+), 52 deletions(-) create mode 100644 test/tests/tagSelectorTest.js diff --git a/chrome/content/zotero/bindings/tagselector.xml b/chrome/content/zotero/bindings/tagselector.xml index 09cde1350..a0c79881e 100644 --- a/chrome/content/zotero/bindings/tagselector.xml +++ b/chrome/content/zotero/bindings/tagselector.xml @@ -132,7 +132,7 @@ if (!this._scope[tag.tag]) { this._scope[tag.tag] = []; } - this._scope[tag.tag].push(tag.type); + this._scope[tag.tag].push(tag.type || 0); } } else { @@ -174,7 +174,11 @@ @@ -455,12 +459,32 @@ this.id('no-tags-deck').selectedIndex = 1; Zotero.debug("Loaded tag selector in " + (new Date - t) + " ms"); + + var event = new Event('refresh'); + this.dispatchEvent(event); }, this); ]]> + + + + + { + if (a.priority === false && b.priority === false) return 0; + if (a.priority === false) return 1; + if (b.priority === false) return -1; + return a.priority - b.priority; + }); + return order.map(o => o.id); + } + + + this.untrigger = function (event, type, ids) { if (!_inTransaction) { throw ("Zotero.Notifier.untrigger() called with no active event queue") } diff --git a/chrome/content/zotero/zoteroPane.js b/chrome/content/zotero/zoteroPane.js index 57e89946b..66c2c91f6 100644 --- a/chrome/content/zotero/zoteroPane.js +++ b/chrome/content/zotero/zoteroPane.js @@ -1128,8 +1128,8 @@ var ZoteroPane = new function() }); if (deferred.promise.isPending()) { Zotero.debug("Waiting for items view " + this.itemsView.id + " to finish loading"); + yield deferred.promise; } - yield deferred.promise; this.itemsView.unregister(); document.getElementById('zotero-items-tree').view = this.itemsView = null; diff --git a/test/tests/collectionTreeViewTest.js b/test/tests/collectionTreeViewTest.js index c2ba0befb..3459a7272 100644 --- a/test/tests/collectionTreeViewTest.js +++ b/test/tests/collectionTreeViewTest.js @@ -3,7 +3,6 @@ describe("Zotero.CollectionTreeView", function() { var win, collectionsView; - // Load Zotero pane and select library before(function* () { win = yield loadZoteroPane(); collectionsView = win.ZoteroPane.collectionsView; @@ -140,13 +139,13 @@ describe("Zotero.CollectionTreeView", function() { var collection = new Zotero.Collection; collection.name = "Test"; var collectionID = yield collection.saveTx(); - var cv = win.ZoteroPane.collectionsView; var search = new Zotero.Search; search.name = "A Test Search"; search.addCondition('title', 'contains', 'test'); var searchID = yield search.saveTx(); + var cv = win.ZoteroPane.collectionsView; var collectionRow = cv._rowMap["C" + collectionID]; var searchRow = cv._rowMap["S" + searchID]; var duplicatesRow = cv._rowMap["D" + Zotero.Libraries.userLibraryID]; diff --git a/test/tests/tagSelectorTest.js b/test/tests/tagSelectorTest.js new file mode 100644 index 000000000..4dfacd0cc --- /dev/null +++ b/test/tests/tagSelectorTest.js @@ -0,0 +1,145 @@ +"use strict"; + +describe("Tag Selector", function () { + var win, doc, collectionsView; + + before(function* () { + win = yield loadZoteroPane(); + doc = win.document; + collectionsView = win.ZoteroPane.collectionsView; + + // Wait for things to settle + yield Zotero.Promise.delay(100); + }); + after(function () { + win.close(); + }); + + function waitForTagSelector() { + var deferred = Zotero.Promise.defer(); + var tagSelector = doc.getElementById('zotero-tag-selector'); + var onRefresh = function (event) { + tagSelector.removeEventListener('refresh', onRefresh); + deferred.resolve(); + } + tagSelector.addEventListener('refresh', onRefresh); + return deferred.promise; + } + + describe("#notify()", function () { + it("should add a tag when added to an item in the current view", function* () { + var promise, tagSelector; + + if (collectionsView.selection.currentIndex != 0) { + promise = waitForTagSelector(); + yield collectionsView.selectLibrary(); + yield promise; + } + + // Add item with tag to library root + var item = createUnsavedDataObject('item'); + item.setTags([ + { + tag: 'A' + } + ]); + promise = waitForTagSelector(); + yield item.saveTx(); + yield promise; + + // Tag selector should have at least one tag + tagSelector = doc.getElementById('zotero-tag-selector'); + assert.isAbove(tagSelector.getVisible().length, 0); + + // Add collection + promise = waitForTagSelector(); + var collection = yield createDataObject('collection'); + yield promise; + + // Tag selector should be empty in new collection + tagSelector = doc.getElementById('zotero-tag-selector'); + assert.equal(tagSelector.getVisible().length, 0); + + // Add item with tag to collection + var item = createUnsavedDataObject('item'); + item.setTags([ + { + tag: 'B' + } + ]); + item.setCollections([collection.id]); + promise = waitForTagSelector() + yield item.saveTx(); + yield promise; + + // Tag selector should show the new item's tag + tagSelector = doc.getElementById('zotero-tag-selector'); + assert.equal(tagSelector.getVisible().length, 1); + }) + + it("should remove a tag when an item is removed from a collection", function* () { + // Add collection + var promise = waitForTagSelector(); + var collection = yield createDataObject('collection'); + yield promise; + + // Add item with tag to collection + var item = createUnsavedDataObject('item'); + item.setTags([ + { + tag: 'A' + } + ]); + item.setCollections([collection.id]); + promise = waitForTagSelector() + yield item.saveTx(); + yield promise; + + // Tag selector should show the new item's tag + var tagSelector = doc.getElementById('zotero-tag-selector'); + assert.equal(tagSelector.getVisible().length, 1); + + item.setCollections(); + promise = waitForTagSelector(); + yield item.saveTx(); + yield promise; + + // Tag selector shouldn't show the removed item's tag + tagSelector = doc.getElementById('zotero-tag-selector'); + assert.equal(tagSelector.getVisible().length, 0); + }) + + it("should remove a tag when an item in a collection is moved to the trash", function* () { + // Add collection + var promise = waitForTagSelector(); + var collection = yield createDataObject('collection'); + yield promise; + + // Add item with tag to collection + var item = createUnsavedDataObject('item'); + item.setTags([ + { + tag: 'A' + } + ]); + item.setCollections([collection.id]); + promise = waitForTagSelector() + yield item.saveTx(); + yield promise; + + // Tag selector should show the new item's tag + var tagSelector = doc.getElementById('zotero-tag-selector'); + assert.equal(tagSelector.getVisible().length, 1); + + // Move item to trash + item.deleted = true; + promise = waitForTagSelector(); + yield item.saveTx(); + yield promise; + + // Tag selector shouldn't show the deleted item's tag + tagSelector = doc.getElementById('zotero-tag-selector'); + assert.equal(tagSelector.getVisible().length, 0); + }) + }) +})