diff --git a/web/app/static/js/modules/corpus_analysis/client/callbacks.js b/web/app/static/js/modules/corpus_analysis/client/callbacks.js index 52d5d61af232893be56cf401595d9ccfbe40d4c3..66fe3c8f1410a60d610100e665ed9af5a9a21252 100644 --- a/web/app/static/js/modules/corpus_analysis/client/callbacks.js +++ b/web/app/static/js/modules/corpus_analysis/client/callbacks.js @@ -2,6 +2,7 @@ * This callback is called on a socket.on "corpus_analysis_send_meta_data". * Handels incoming corpus metadata */ +// TODO: rework arguments to ...args function saveMetaData() { let [payload, client, results, rest] = arguments; client.notifyView('meta-data-recieving'); diff --git a/web/app/static/js/modules/corpus_analysis/view/ResultsView.js b/web/app/static/js/modules/corpus_analysis/view/ResultsView.js index b799ff2b92ce613572e349e9ca3db4a3865673fb..adab3ee75cc7515c835e80bacada5a1c46c06624 100644 --- a/web/app/static/js/modules/corpus_analysis/view/ResultsView.js +++ b/web/app/static/js/modules/corpus_analysis/view/ResultsView.js @@ -3,9 +3,10 @@ * specified */ class ViewEventListener { - constructor(type, listenerFunction) { + constructor(type, listenerFunction, args=[]) { this.listenerFunction = listenerFunction; this.type = type; + this.args = args; } } @@ -139,7 +140,11 @@ class ResultsList extends List { */ loadViewEventListeners() { for (let [type, listener] of Object.entries(this.notificationListeners)) { - listener.listenerFunction(type, this); + if (listener.args.length > 0) { + listener.listenerFunction(...listener.args); + } else { + listener.listenerFunction(type, this); + } } } diff --git a/web/app/static/js/modules/corpus_analysis/view/eventListeners.js b/web/app/static/js/modules/corpus_analysis/view/eventListeners.js deleted file mode 100644 index 2316505727a7ac25296ede89f101b56a8ca5a710..0000000000000000000000000000000000000000 --- a/web/app/static/js/modules/corpus_analysis/view/eventListeners.js +++ /dev/null @@ -1,273 +0,0 @@ -/** -* This module contains vanilla javascript Event listeners which are listening -* for button clicks etc. the user is doing to interact with the page. -*/ - -// Import the script that implements a spinner animation for buttons. -import { - loadingSpinnerHTML, -} from './spinner.js'; - -/** - * The following listener handles what functions are called when the user - * does use the page navigation to navigate to a new page. - */ -function pageNavigation(resultsList, results, client) { - for (let element of resultsList.pagination) { - element.addEventListener("click", (event) => { - // Shows match context according to the user picked value on a new page. - resultsList.changeContext(); - // De- or activates expertMode on new page depending on switch value. - if (resultsList.displayOptionsFormExpertMode.checked) { - resultsList.expertModeOn('query-display', results); - } else { - resultsList.expertModeOff('query-display'); - } - // Activates inspect buttons on new page if client is not busy. - resultsList.toggleInspectButtons(client); - }); - } -} - -/** - * The following event Listener handles the expert mode switch for the list. - */ -function expertModeSwitch(resultsList, results) { - resultsList.displayOptionsFormExpertMode.onchange = (event) => { - if (event.target.checked) { - resultsList.expertModeOn('query-display', results); - } else { - resultsList.expertModeOff('query-display'); - } - }; -} - -/** - * The following event Listener handles the add-btn and the inspect-btn - * onclick events via bubbleing. - */ -function actionButtons(resultsList, results, client) { - resultsList.queryResultsTable.addEventListener('click', (event) => { - let dataIndex; - if (event.target.classList.contains('inspect-btn')) { - dataIndex = parseInt(event.target.closest('tr').dataset.index); - resultsList.inspect(client, results, [dataIndex], 'inspect'); - } else if (event.target.classList.contains('add-btn')) { - dataIndex = parseInt(event.target.closest('tr').dataset.index); - resultsList.addToSubResults(dataIndex, client); - } - }) -} - -/** - * Following event listeners handle the change of Context size per match and - * the number of matches shown per page. - */ -function displayOptions(resultsList, results, client) { - resultsList.displayOptionsFormResultsPerPage.onchange = (event) => { - resultsList.changeHitsPerPage(client, results); - }; - resultsList.displayOptionsFormResultContext.onchange = (event) => { - resultsList.changeContext(); - }; -} - -/** - * The following event listener handles the show metadata button and its - * functionality. - */ -function showMetaData(resultsList, results) { - resultsList.showMetaData.onclick = () => { - resultsList.metaDataModalContent.textContent = ''; - let table = resultsList.createMetaDataForModal(results.metaData); - resultsList.metaDataModalContent.insertAdjacentHTML('afterbegin', table); - resultsList.metaDataModal.open(); - let collapsibles = resultsList.metaDataModalContent.querySelectorAll(".text-metadata"); - for (let collapsible of collapsibles) { - collapsible.onclick = () => { - let elems = resultsList.metaDataModalContent.querySelectorAll('.collapsible'); - let instances = M.Collapsible.init(elems, {accordion: false}); - resultsList.createTextDetails(results.metaData); - } - } - }; -} - -/** - * The following event listener handles the button showing infos about matches - * and their corresponding corpus files - */ - -function showCorpusFiles(resultsList, results) { - resultsList.showCorpusFiles.onclick = () => { - resultsList.showCorpusFilesModalContent.innerHTML = ''; - let htmlString = ` - <div id="corpus-file-table"> - <ul class="pagination paginationTop"></ul> - <table class="responsive-table highlight"> - <thead> - <tr> - <th class="sort" data-sort="title">Title</th> - <th class="sort" data-sort="year">Year</th> - <th class="sort" data-sort="match-count">Match count in this text</th> - </tr> - </thead> - <tbody class="list"> - ` - for (let [key, value] of Object.entries(results.data.text_lookup)) { - htmlString += ` - <tr> - <td class="title">${value.title}</td> - <td class="year">${value.publishing_year}</td> - <td class="match-count">${value.match_count}</td> - </tr> - ` - } - htmlString += ` - </tbody> - </table> - <ul class="pagination paginationBottom"></ul> - </div> - ` - resultsList.showCorpusFilesModalContent.insertAdjacentHTML('afterbegin', htmlString); - resultsList.showCorpusFilesModal.open(); - let options = { - page: 10, - pagination: [{ - name: "paginationTop", - paginationClass: "paginationTop", - innerWindow: 8, - outerWindow: 1 - }, { - paginationClass: "paginationBottom", - innerWindow: 8, - outerWindow: 1 - }], - valueNames: ["title", "year", "match-count"], - }; - let corpusFileTable = new List('corpus-file-table', options); - console.log(corpusFileTable); - } -} - -/** - * Checks if resultsList.exportFullInspectContext switch is changed. - * If it has been changed reset all Download buttons. - */ -function exportFullContextSwitch(resultsList) { - resultsList.exportFullInspectContext.onchange = (event) => { - // Hide all download buttons. - resultsList.fullResultsExport.classList.toggle('hide', true); - resultsList.subResultsExport.classList.toggle('hide', true); - // Show result create buttons. - resultsList.fullResultsCreate.classList.toggle('hide', false); - resultsList.subResultsCreate.classList.toggle('hide', false); - } -} - -/** - * The following event listeners are handeling the data export. - * 1. Create full-results - * 2. Create sub-results - * 3. Download full-results - * 4. Download sub-results - * 5. Download single inspect-results - */ - -// 1. Add events for full-results create -function createFullResults(resultsList, results) { - resultsList.fullResultsCreate.onclick = (event) => { - resultsList.fullResultsCreate.querySelector('i').classList.toggle('hide'); - resultsList.fullResultsCreate.innerText = 'Creating...'; - resultsList.fullResultsCreate.insertAdjacentHTML('afterbegin', - loadingSpinnerHTML); - // .keys() is for a zero based array. I think... - let dataIndexes = [...Array(results.data.match_count).keys()]; - // Empty fullResultsData so that no previous data is used. - results.fullResultsData.init(); - resultsList.notifyClient('get-results', {resultsType: 'full-results', - dataIndexes: dataIndexes, - resultsList: resultsList,}); - } -} - -// 2. Add events for sub-results create -function createSubResults(resultsList, results) { - resultsList.subResultsCreate.onclick = (event) => { - let dataIndexes = []; - Object.keys(resultsList.subResultsIndexes).forEach((id) => { - dataIndexes.push(id); - }); - resultsList.subResultsCreate.querySelector('i').classList.toggle('hide'); - resultsList.subResultsCreate.innerText = 'Creating...'; - resultsList.subResultsCreate.insertAdjacentHTML('afterbegin', - loadingSpinnerHTML); - // Empty subResultsData so that no previous data is used. - results.subResultsData.init(); - resultsList.notifyClient('get-results', {resultsType: 'sub-results', - dataIndexes: dataIndexes, - resultsList: resultsList,}); - } -} -// 3. Open download modal when full results export button is pressed -function exportFullResults(resultsList, results) { - resultsList.fullResultsExport.onclick = (event) => { - resultsList.queryResultsDownloadModal.open(); - // add onclick to download JSON button and download the file - resultsList.downloadResultsJson.onclick = (event) => { - let suffix = 'full-results' - if (resultsList.exportFullInspectContext.checked) { - suffix += '_full-context'; - } - let filename = results.fullResultsData.createDownloadFilename(suffix); - results.fullResultsData.addData(results.metaData); - results.fullResultsData.downloadJSONRessource(filename, - results.fullResultsData, - resultsList.downloadResultsJson)}; - } -} -// 4. Open download modal when sub results export button is pressed -function exportSubResults(resultsList, results) { - resultsList.subResultsExport.onclick = (event) => { - resultsList.queryResultsDownloadModal.open(); - // add onclick to download JSON button and download the file - resultsList.downloadResultsJson.onclick = (event) => { - let suffix = 'sub-results' - if (resultsList.exportFullInspectContext.checked) { - suffix += '_full-context'; - } - let filename = results.subResultsData.createDownloadFilename(suffix); - results.subResultsData.addData(results.metaData); - results.subResultsData.downloadJSONRessource(filename, - results.subResultsData, - resultsList.downloadResultsJson)}; - } -} -// 5. Open download modal when inspect-results-export button is pressed -function exportSingleMatch(resultsList, results) { - resultsList.inspectResultsExport.onclick = (event) => { - resultsList.queryResultsDownloadModal.open(); - // add onclick to download JSON button and download the file - resultsList.downloadResultsJson.onclick = (event) => { - let filename = results.subResultsData.createDownloadFilename('inspect-results_full-context'); - results.subResultsData.addData(results.metaData); - results.subResultsData.downloadJSONRessource(filename, - results.inspectResultsData, - resultsList.downloadResultsJson)}; - } -} - -export { - pageNavigation, - expertModeSwitch, - actionButtons, - displayOptions, - showMetaData, - showCorpusFiles, - exportFullContextSwitch, - createFullResults, - createSubResults, - exportFullResults, - exportSubResults, - exportSingleMatch, -} diff --git a/web/app/static/js/modules/corpus_analysis/view/listeners.js b/web/app/static/js/modules/corpus_analysis/view/listeners.js index 24aa51a3598fec442f7ebcc0ca5dd9516a2dac2b..5df70baa5f09c541a994b0db80704897479bcbe7 100644 --- a/web/app/static/js/modules/corpus_analysis/view/listeners.js +++ b/web/app/static/js/modules/corpus_analysis/view/listeners.js @@ -1,10 +1,15 @@ /** + * 1.) * This file contains the listener function that will be assigned to the * corpus_analysis ResultsView. The listener is listening for the notification * event which is being dispatched by the corpus_analysis Client. The * notification Event triggers the listener which will call different * callback functions depending on the detail information of the notification * event. + * 2.) + * This file also contains vanilla javascript Event listeners which are + * listening for button clicks etc. the user is doing for page interaction. + * They will be registered the same way as teh listeners above. */ import { @@ -20,7 +25,16 @@ import { disableElementsGeneralCallback, enableElementsGeneralCallback, } from './callbacks.js'; +// Import the script that implements a spinner animation for buttons. +import { + loadingSpinnerHTML, +} from './spinner.js'; + +/** + * The Listener listening for the notification event 'notify-view' dispatched + * by the client and execeutes callbacks accordingly. + */ function recieveClientNotification(eventType, resultsList) { document.addEventListener(eventType, (event) => { let caseIdentifier = event.detail.caseIdentifier; @@ -92,5 +106,274 @@ function recieveClientNotification(eventType, resultsList) { }); } +/** + * This are some vanilla javascript Event listeners which are listening + * for button clicks etc. the user is doing to interact with the page. + * They will be registered the same way as the listeners above. + */ + +/** + * The following listener handles what functions are called when the user + * does use the page navigation to navigate to a new page. + */ +function pageNavigation(resultsList, results, client) { + for (let element of resultsList.pagination) { + element.addEventListener("click", (event) => { + // Shows match context according to the user picked value on a new page. + resultsList.changeContext(); + // De- or activates expertMode on new page depending on switch value. + if (resultsList.displayOptionsFormExpertMode.checked) { + resultsList.expertModeOn('query-display', results); + } else { + resultsList.expertModeOff('query-display'); + } + // Activates inspect buttons on new page if client is not busy. + resultsList.toggleInspectButtons(client); + }); + } +} + +/** + * The following event Listener handles the expert mode switch for the list. + */ +function expertModeSwitch(resultsList, results) { + resultsList.displayOptionsFormExpertMode.onchange = (event) => { + if (event.target.checked) { + resultsList.expertModeOn('query-display', results); + } else { + resultsList.expertModeOff('query-display'); + } + }; +} + +/** + * The following event Listener handles the add-btn and the inspect-btn + * onclick events via bubbleing. + */ +function actionButtons(resultsList, results, client) { + resultsList.queryResultsTable.addEventListener('click', (event) => { + let dataIndex; + if (event.target.classList.contains('inspect-btn')) { + dataIndex = parseInt(event.target.closest('tr').dataset.index); + resultsList.inspect(client, results, [dataIndex], 'inspect'); + } else if (event.target.classList.contains('add-btn')) { + dataIndex = parseInt(event.target.closest('tr').dataset.index); + resultsList.addToSubResults(dataIndex, client); + } + }) +} + +/** + * Following event listeners handle the change of Context size per match and + * the number of matches shown per page. + */ +function displayOptions(resultsList, results, client) { + resultsList.displayOptionsFormResultsPerPage.onchange = (event) => { + resultsList.changeHitsPerPage(client, results); + }; + resultsList.displayOptionsFormResultContext.onchange = (event) => { + resultsList.changeContext(); + }; +} + +/** + * The following event listener handles the show metadata button and its + * functionality. + */ +function showMetaData(resultsList, results) { + resultsList.showMetaData.onclick = () => { + resultsList.metaDataModalContent.textContent = ''; + let table = resultsList.createMetaDataForModal(results.metaData); + resultsList.metaDataModalContent.insertAdjacentHTML('afterbegin', table); + resultsList.metaDataModal.open(); + let collapsibles = resultsList.metaDataModalContent.querySelectorAll(".text-metadata"); + for (let collapsible of collapsibles) { + collapsible.onclick = () => { + let elems = resultsList.metaDataModalContent.querySelectorAll('.collapsible'); + let instances = M.Collapsible.init(elems, {accordion: false}); + resultsList.createTextDetails(results.metaData); + } + } + }; +} + +/** + * The following event listener handles the button showing infos about matches + * and their corresponding corpus files + */ + +function showCorpusFiles(resultsList, results) { + resultsList.showCorpusFiles.onclick = () => { + resultsList.showCorpusFilesModalContent.innerHTML = ''; + let htmlString = ` + <div id="corpus-file-table"> + <ul class="pagination paginationTop"></ul> + <table class="responsive-table highlight"> + <thead> + <tr> + <th class="sort" data-sort="title">Title</th> + <th class="sort" data-sort="year">Year</th> + <th class="sort" data-sort="match-count">Match count in this text</th> + </tr> + </thead> + <tbody class="list"> + ` + for (let [key, value] of Object.entries(results.data.text_lookup)) { + htmlString += ` + <tr> + <td class="title">${value.title}</td> + <td class="year">${value.publishing_year}</td> + <td class="match-count">${value.match_count}</td> + </tr> + ` + } + htmlString += ` + </tbody> + </table> + <ul class="pagination paginationBottom"></ul> + </div> + ` + resultsList.showCorpusFilesModalContent.insertAdjacentHTML('afterbegin', htmlString); + resultsList.showCorpusFilesModal.open(); + let options = { + page: 10, + pagination: [{ + name: "paginationTop", + paginationClass: "paginationTop", + innerWindow: 8, + outerWindow: 1 + }, { + paginationClass: "paginationBottom", + innerWindow: 8, + outerWindow: 1 + }], + valueNames: ["title", "year", "match-count"], + }; + let corpusFileTable = new List('corpus-file-table', options); + console.log(corpusFileTable); + } +} + +/** + * Checks if resultsList.exportFullInspectContext switch is changed. + * If it has been changed reset all Download buttons. + */ +function exportFullContextSwitch(resultsList) { + resultsList.exportFullInspectContext.onchange = (event) => { + // Hide all download buttons. + resultsList.fullResultsExport.classList.toggle('hide', true); + resultsList.subResultsExport.classList.toggle('hide', true); + // Show result create buttons. + resultsList.fullResultsCreate.classList.toggle('hide', false); + resultsList.subResultsCreate.classList.toggle('hide', false); + } +} + +/** + * The following event listeners are handeling the data export. + * 1. Create full-results + * 2. Create sub-results + * 3. Download full-results + * 4. Download sub-results + * 5. Download single inspect-results + */ + +// 1. Add events for full-results create +function createFullResults(resultsList, results) { + resultsList.fullResultsCreate.onclick = (event) => { + resultsList.fullResultsCreate.querySelector('i').classList.toggle('hide'); + resultsList.fullResultsCreate.innerText = 'Creating...'; + resultsList.fullResultsCreate.insertAdjacentHTML('afterbegin', + loadingSpinnerHTML); + // .keys() is for a zero based array. I think... + let dataIndexes = [...Array(results.data.match_count).keys()]; + // Empty fullResultsData so that no previous data is used. + results.fullResultsData.init(); + resultsList.notifyClient('get-results', {resultsType: 'full-results', + dataIndexes: dataIndexes, + resultsList: resultsList,}); + } +} + +// 2. Add events for sub-results create +function createSubResults(resultsList, results) { + resultsList.subResultsCreate.onclick = (event) => { + let dataIndexes = []; + Object.keys(resultsList.subResultsIndexes).forEach((id) => { + dataIndexes.push(id); + }); + resultsList.subResultsCreate.querySelector('i').classList.toggle('hide'); + resultsList.subResultsCreate.innerText = 'Creating...'; + resultsList.subResultsCreate.insertAdjacentHTML('afterbegin', + loadingSpinnerHTML); + // Empty subResultsData so that no previous data is used. + results.subResultsData.init(); + resultsList.notifyClient('get-results', {resultsType: 'sub-results', + dataIndexes: dataIndexes, + resultsList: resultsList,}); + } +} +// 3. Open download modal when full results export button is pressed +function exportFullResults(resultsList, results) { + resultsList.fullResultsExport.onclick = (event) => { + resultsList.queryResultsDownloadModal.open(); + // add onclick to download JSON button and download the file + resultsList.downloadResultsJson.onclick = (event) => { + let suffix = 'full-results' + if (resultsList.exportFullInspectContext.checked) { + suffix += '_full-context'; + } + let filename = results.fullResultsData.createDownloadFilename(suffix); + results.fullResultsData.addData(results.metaData); + results.fullResultsData.downloadJSONRessource(filename, + results.fullResultsData, + resultsList.downloadResultsJson)}; + } +} +// 4. Open download modal when sub results export button is pressed +function exportSubResults(resultsList, results) { + resultsList.subResultsExport.onclick = (event) => { + resultsList.queryResultsDownloadModal.open(); + // add onclick to download JSON button and download the file + resultsList.downloadResultsJson.onclick = (event) => { + let suffix = 'sub-results' + if (resultsList.exportFullInspectContext.checked) { + suffix += '_full-context'; + } + let filename = results.subResultsData.createDownloadFilename(suffix); + results.subResultsData.addData(results.metaData); + results.subResultsData.downloadJSONRessource(filename, + results.subResultsData, + resultsList.downloadResultsJson)}; + } +} +// 5. Open download modal when inspect-results-export button is pressed +function exportSingleMatch(resultsList, results) { + resultsList.inspectResultsExport.onclick = (event) => { + resultsList.queryResultsDownloadModal.open(); + // add onclick to download JSON button and download the file + resultsList.downloadResultsJson.onclick = (event) => { + let filename = results.subResultsData.createDownloadFilename('inspect-results_full-context'); + results.subResultsData.addData(results.metaData); + results.subResultsData.downloadJSONRessource(filename, + results.inspectResultsData, + resultsList.downloadResultsJson)}; + } +} + // export listeners -export { recieveClientNotification }; \ No newline at end of file +export { + recieveClientNotification, + pageNavigation, + expertModeSwitch, + actionButtons, + displayOptions, + showMetaData, + showCorpusFiles, + exportFullContextSwitch, + createFullResults, + createSubResults, + exportFullResults, + exportSubResults, + exportSingleMatch, +}; \ No newline at end of file diff --git a/web/app/templates/corpora/analyse_corpus.html.j2 b/web/app/templates/corpora/analyse_corpus.html.j2 index 7681495d3c744c5a2d3ea41d376f4c72238d1922..c127b6f52c7e9ac8436680e6345c00fc03e34e23 100644 --- a/web/app/templates/corpora/analyse_corpus.html.j2 +++ b/web/app/templates/corpora/analyse_corpus.html.j2 @@ -115,14 +115,9 @@ import { } from '../../static/js/modules/corpus_analysis/view/ResultsView.js'; // Import listener which will be registered to the ViewEventListener class. import { + // listener listening for client dispatched 'notify-vie' custom event. recieveClientNotification, -} from '../../static/js/modules/corpus_analysis/view/listeners.js'; -// Import script that implements the scroll to top button. -import { - scrollToTop, -} from '../../static/js/modules/corpus_analysis/view/scrollToTop.js'; -// vanilla javascript Event listeners which are listening for button clicks etc -import { + // vanilla javascript Event listeners which are listening for button clicks. pageNavigation, expertModeSwitch, actionButtons, @@ -135,7 +130,13 @@ import { exportFullResults, exportSubResults, exportSingleMatch, -} from '../../static/js/modules/corpus_analysis/view/eventListeners.js'; +} from '../../static/js/modules/corpus_analysis/view/listeners.js'; +// Import script that implements the scroll to top button. +import { + scrollToTop, +} from '../../static/js/modules/corpus_analysis/view/scrollToTop.js'; +// vanilla javascript Event listeners which are listening for button clicks etc + /** * Second Phase: @@ -208,35 +209,11 @@ document.addEventListener("DOMContentLoaded", () => { */ const listenForClientNotification = new ViewEventListener('notify-view', recieveClientNotification); - resultsList.setViewEventListeners([listenForClientNotification]); - resultsList.loadViewEventListeners(); - // Connect client to server. - client.notifyView('connecting'); - client.connect(); - // Send a query and recieve its answer data. - let queryFormElement = document.querySelector('#query-form'); - queryFormElement.addEventListener('submit', (event) => { - try { - /** - * Selects first page of result list if pagination is already available - * from an query submitted before. - * This avoids confusion for the user e.g.: The user was on page 24 - * reviewing the results and issues a new query. He would not see any - * results until the new results reach page 24 or he clicks on another - * valid result page element from the new pagination. - */ - let firstPageElement = document.querySelector('a.page'); - firstPageElement.click(); - } catch (e) { - // No page element is present if first query is submitted. - } - // Prevent page from reloading on submit. - event.preventDefault(); - // Get query string and send query to server. - results.data.getQueryStr(queryFormElement); - client.query(results.data.query); - }); - // Get all needed HTMLElements for the following event listeners. + /** + * Register vanilla Javascript events to the resultList listening for button + * clicks etc. done by the user. + * Get all needed HTMLElements for those event listeners before. + */ resultsList.getHTMLElements([ '.pagination', '#display-options-form-expert_mode', @@ -270,21 +247,86 @@ document.addEventListener("DOMContentLoaded", () => { '#sub-results-export', '#export-full-inspect-context', ]); - - // Call the vanilla event listeners listening for clicks etc. from the user. - pageNavigation(resultsList, results, client); - expertModeSwitch(resultsList, results); - actionButtons(resultsList, results, client); - displayOptions(resultsList, results, client); - showMetaData(resultsList, results); - showCorpusFiles(resultsList, results); - // Still vanilla event listeners, but focused on result download and export - exportFullContextSwitch(resultsList); - createFullResults(resultsList, results); - createSubResults(resultsList, results); - exportFullResults(resultsList, results); - exportSubResults(resultsList, results); - exportSingleMatch(resultsList, results); + let args = [resultsList, results, client] + const listenForPageNavigation = new ViewEventListener('page-navigation', + pageNavigation, + args); + const listenForExpertModeSwitch = new ViewEventListener('expert-mode', + expertModeSwitch, + args); + const listenForActionButtons = new ViewEventListener('action-buttons', + actionButtons, + args); + const listenForDisplayOptions = new ViewEventListener('display-otions', + displayOptions, + args); + const listenForShowMetaData = new ViewEventListener('show-meta-data', + showMetaData, + args); + const listenForShowCorpusFiles = new ViewEventListener('show-corpus-files', + showCorpusFiles, + args); + const listenForExportFullContextSwitch = new ViewEventListener('export-full-context-switch', + exportFullContextSwitch, + args); + const listenForCreateFullResults = new ViewEventListener('create-full-results', + createFullResults, + args); + const listenForCreateSubResults = new ViewEventListener('create-sub-results', + createSubResults, + args); + const listenForExportFullResults = new ViewEventListener('export-full-results', + exportFullResults, + args); + const listenForExportSubResults = new ViewEventListener('export-sub-results', + exportSubResults, + args); + const listenForExportSingleMatch = new ViewEventListener('export-single-match', + exportSingleMatch, + args); + // Set and load define listeners + resultsList.setViewEventListeners([ + listenForClientNotification, + listenForPageNavigation, + listenForExpertModeSwitch, + listenForActionButtons, + listenForDisplayOptions, + listenForShowMetaData, + listenForShowCorpusFiles, + listenForExportFullContextSwitch, + listenForCreateFullResults, + listenForCreateSubResults, + listenForExportFullResults, + listenForExportSubResults, + listenForExportSingleMatch, + ]); + resultsList.loadViewEventListeners(); + // Connect client to server. + client.notifyView('connecting'); + client.connect(); + // Send a query and recieve its answer data. + let queryFormElement = document.querySelector('#query-form'); + queryFormElement.addEventListener('submit', (event) => { + try { + /** + * Selects first page of result list if pagination is already available + * from an query submitted before. + * This avoids confusion for the user e.g.: The user was on page 24 + * reviewing the results and issues a new query. He would not see any + * results until the new results reach page 24 or he clicks on another + * valid result page element from the new pagination. + */ + let firstPageElement = document.querySelector('a.page'); + firstPageElement.click(); + } catch (e) { + // No page element is present if first query is submitted. + } + // Prevent page from reloading on submit. + event.preventDefault(); + // Get query string and send query to server. + results.data.getQueryStr(queryFormElement); + client.query(results.data.query); + }); // Enable scroll to Top functionality. scrollToTop('#headline', '#menu-scroll-to-top-div'); });