diff --git a/Gulpfile.js b/Gulpfile.js index 33ccfd6..653f632 100644 --- a/Gulpfile.js +++ b/Gulpfile.js @@ -72,7 +72,8 @@ gulp.task('dist-node-modules', function () { 'node_modules/ngstorage/ngStorage.js', 'node_modules/node-uuid/uuid.js', 'node_modules/rangy/lib/rangy-core.js', - 'node_modules/rangy/lib/rangy-serializer.js' + 'node_modules/rangy/lib/rangy-serializer.js', + 'node_modules/rangy/lib/rangy-selectionsaverestore.js' ], {base: 'node_modules'}) .pipe($.sourcemaps.init()) .pipe($.concat('vendor.js')) @@ -94,8 +95,9 @@ gulp.task('serve', ['tmp'], function () { // Serve files from the root of this project browserSync.init({ server: { - baseDir: "./tmp", - } + baseDir: "./tmp" + }, + notify: false }); // add browserSync.reload to the tasks array to make diff --git a/src/index.html b/src/index.html index 7484b02..4c788c3 100644 --- a/src/index.html +++ b/src/index.html @@ -30,7 +30,7 @@

Sample text

- The Triumph of Cleopatra, also known as Cleopatra's Arrival in Cilicia[1] and The Arrival of Cleopatra in Cilicia,[2] is an oil painting by English artist William Etty. It was first exhibited in 1821, and is now in the Lady Lever Art Gallery in Port Sunlight across the River Mersey from Liverpool. During the 1810s Etty had become widely respected among staff and students at the Royal Academy of Arts, in particular for his use of colour and ability to paint realistic flesh tones. Despite having exhibited at every Summer Exhibition since 1811 he attracted little commercial or critical interest. In 1820 he exhibited The Coral Finder, which showed nude figures on a gilded boat. This painting attracted the attention of Sir Francis Freeling, who commissioned a similar painting on a more ambitious scale. + The Triumph of Cleopatra, also known as Cleopatra's Arrival in Cilicia[1] and The Arrival of Cleopatra in Cilicia,[2] is an oil painting by English artist William Etty. It was first exhibited in 1821, and is now in the Lady Lever Art Gallery in Port Sunlight across the River Mersey from Liverpool. During the 1810s Etty had become widely respected among staff and students at the Royal Academy of Arts, in particular for his use of colour and ability to paint realistic flesh tones. Despite having exhibited at every Summer Exhibition since 1811 he attracted little commercial or critical interest. In 1820 he exhibited The Coral Finder, which showed nude figures on a gilded boat. This painting attracted the attention of Sir Francis Freeling, who commissioned a similar painting on a more ambitious scale.

Rome's history spans more than two and a half thousand years. While Roman mythology dates the founding of Rome at only around 753 BC, the site has been inhabited for much longer, making it one of the oldest continuously occupied sites in Europe.[5] The city's early population originated from a mix of Latins, Etruscans and Sabines. Eventually, the city successively became the capital of the Roman Kingdom, the Roman Republic and the Roman Empire, and is regarded as one of the birthplaces of Western civilization and as the first ever metropolis.[6] It is referred to as "Roma Aeterna" (The Eternal City) [7] and "Caput Mundi" (Capital of the World), two central notions in ancient Roman culture. diff --git a/src/menu/menu.controller.ts b/src/menu/menu.controller.ts index 0897da3..6615171 100644 --- a/src/menu/menu.controller.ts +++ b/src/menu/menu.controller.ts @@ -41,9 +41,19 @@ module tagIt { } onSenseSelect (sense: ISense) { - var senseTag = this.webPageService.addNewTagToPage(sense); - this.tagStorageService.saveTag(senseTag) + //remove all tags so that new tag range is serialized + //based on a document without any highlights + this.webPageService.removeAllTagsFromPage(); + + //initialize and save the new tag + var senseTag = this.webPageService.initializeNewTag(sense); + this.tagStorageService.saveTag(senseTag); this.backendService.sendTaggedDataToServer(senseTag); + + //re-add tags, with new tag. Clear menu options. + this.webPageService.readdTagsToPage( + this.tagStorageService.loadTags() + ); this.clearMenuVariables(); } diff --git a/src/services/tagStorage.service.ts b/src/services/tagStorage.service.ts index 1562fcb..c015c06 100644 --- a/src/services/tagStorage.service.ts +++ b/src/services/tagStorage.service.ts @@ -19,11 +19,11 @@ module tagIt { this.$log = $log; this.$localStorage = $localStorage; + // this.deleteTags(); // reset tag storage + if (!this.$localStorage.tagStorage) { this.$localStorage.tagStorage = []; } - - // this.deleteTags(); // reset tag storage } deleteTagById(uuid: string) { @@ -49,11 +49,11 @@ module tagIt { this.$log.debug(tagToSave); this.$localStorage.tagStorage.push(tagToSave); } - + loadTags() { this.$log.debug('loadTags'); return this.$localStorage.tagStorage; } - + } } \ No newline at end of file diff --git a/src/services/webpage.service.ts b/src/services/webpage.service.ts index ac9c09a..c41e578 100644 --- a/src/services/webpage.service.ts +++ b/src/services/webpage.service.ts @@ -14,13 +14,14 @@ module tagIt { $log: ng.ILogService; // when clicking the menu to select a synset // we need to remember what the currently selected word was - currentSelectionRange: any; tagStorageService: TagStorageService; + savedSelection: Object; /* @ngInject */ constructor($log: ng.ILogService, TagStorageService: TagStorageService) { this.$log = $log; this.tagStorageService = TagStorageService; + rangy.init(); } wireUpListener(callbackOnSelectFunc: (result: Object) => void, @@ -37,7 +38,7 @@ module tagIt { this.tagStorageService.deleteTagById(evt.target.parentElement.id); } else if (this.findSelectedText()) { - this.currentSelectionRange = this.getClonedSelectionRange(); + this.savedSelection = rangy.saveSelection(); callbackOnSelectFunc(joinLongWords(this.findSelectedText())); } else { callbackOnDeSelectFunc(); @@ -76,13 +77,16 @@ module tagIt { } // place spans around a tagged word. - addNewTagToPage = (sense: ISense): ISenseTag => { + initializeNewTag = (sense: ISense): ISenseTag => { this.$log.debug('addNewTagToPage'); - var range = this.currentSelectionRange; + rangy.restoreSelection(this.savedSelection); + rangy.removeMarkers(this.savedSelection); + var range = rangy.getSelection().getRangeAt(0); var serializedRange = rangy.serializeRange( range, false, document.getElementById('tagit-body')); var generatedUuid: string = uuid.v4(); - this.surroundRangeWithSpan(sense, range, generatedUuid); + + // this.surroundRangeWithSpan(sense, range, generatedUuid); return { id: generatedUuid, @@ -93,21 +97,44 @@ module tagIt { } }; + removeAllTagsFromPage() { + // find all tags + var elements = document.getElementsByClassName('tagit-tag'); + // remove them from page + for (var i = 0; i < elements.length; i++) { + var tagElement = elements[i]; + var tagElementParentNode = tagElement.parentNode; + tagElementParentNode.replaceChild( + tagElement.previousSibling, + tagElement); + tagElementParentNode.normalize(); + } + } + readdTagsToPage(tagsToLoad: ISenseTag[]) { this.$log.debug('readdTagsToPage()'); //first deselect before we go to work window.getSelection().removeAllRanges(); - var tag: ISenseTag; + var selection = rangy.getSelection(); + for (var i = 0; i < tagsToLoad.length; i++) { - tag = tagsToLoad[i]; + var tag = tagsToLoad[i]; tag.deSerializedSelectionRange = deserializeRange(tag); + } + + this.$log.debug('finished deserializing tags'); + + for (var i = 0; i < tagsToLoad.length; i++) { + var tag = tagsToLoad[i]; if (tag.deSerializedSelectionRange) { this.surroundRangeWithSpan(tag.sense, tag.deSerializedSelectionRange, tag.id); } } + + this.$log.debug('finished adding tags to page'); window.getSelection().removeAllRanges(); @@ -115,7 +142,6 @@ module tagIt { // and connects it to the active page function deserializeRange(tagToLoad: ISenseTag) { var savedRange: Range = undefined - var selection = window.getSelection(); try { savedRange = rangy.deserializeRange( tagToLoad.serializedSelectionRange, @@ -136,35 +162,6 @@ module tagIt { } } - private readdTagToPage(tagToLoad: ISenseTag) { - this.$log.debug('addNewTagToPage'); - var savedRange: Range = undefined - var selection = window.getSelection(); - try { - savedRange = rangy.deserializeRange( - tagToLoad.serializedSelectionRange, - document.getElementById('tagit-body')); - } catch (e) { - this.$log.error('Error in rangy.js: Was not able to deserialize range.'); - this.$log.error('In other words: The page might have changed. Is not able '); - this.$log.error('to determine where this tag should have been placed.'); - this.$log.error(e); - } - - //remove any present selections - selection.removeAllRanges(); - - //select text on page - var rangeToLoad = document.createRange(); - rangeToLoad.setStart(savedRange.startContainer, savedRange.startOffset) - rangeToLoad.setEnd(savedRange.endContainer, savedRange.endOffset); - selection.addRange(rangeToLoad); - - //tag that text with a span and a remove button. - this.surroundRangeWithSpan(tagToLoad.sense, - selection.getRangeAt(0).cloneRange(), tagToLoad.id); - } - private surroundRangeWithSpan(sense: ISense, range: Range, uuid: string) { // add span around content var span: HTMLSpanElement = document.createElement('span');