diff --git a/app/static/js/CorpusAnalysis/QueryBuilder.js b/app/static/js/CorpusAnalysis/QueryBuilder.js
deleted file mode 100644
index b37cdf14dd5f98fa3c736639d92f490667bc9589..0000000000000000000000000000000000000000
--- a/app/static/js/CorpusAnalysis/QueryBuilder.js
+++ /dev/null
@@ -1,52 +0,0 @@
-class ConcordanceQueryBuilder {
-
-  constructor() {
-    
-    this.elements = new ElementReferencesQueryBuilder();
-    this.generalFunctions = new GeneralFunctionsQueryBuilder(this.elements);
-    this.tokenAttributeBuilderFunctions = new TokenAttributeBuilderFunctionsQueryBuilder(this.elements);
-    this.structuralAttributeBuilderFunctions = new StructuralAttributeBuilderFunctionsQueryBuilder(this.elements);
-
-    // Eventlisteners for the incidence modifiers. There are two different types of incidence modifiers: token and character incidence modifiers.
-    document.querySelectorAll('.incidence-modifier-selection').forEach(button => {
-      let dropdownId = button.parentNode.parentNode.id;
-      if (dropdownId === 'corpus-analysis-concordance-token-incidence-modifiers-dropdown') {
-        button.addEventListener('click', () => this.generalFunctions.tokenIncidenceModifierHandler(button.dataset.token, button.innerHTML));
-      } else if (dropdownId === 'corpus-analysis-concordance-character-incidence-modifiers-dropdown') {
-        button.addEventListener('click', () => this.tokenAttributeBuilderFunctions.characterIncidenceModifierHandler(button));
-      }
-    });
-    
-    // Eventlisteners for the submit of n- and m-values of the incidence modifier modal for "exactly n" or "between n and m".
-    document.querySelectorAll('.n-m-submit-button').forEach(button => {
-      let modalId = button.dataset.modalId;
-      if (modalId === 'corpus-analysis-concordance-exactly-n-token-modal' || modalId === 'corpus-analysis-concordance-between-nm-token-modal') {
-        button.addEventListener('click', () => this.generalFunctions.tokenNMSubmitHandler(modalId));
-      } else if (modalId === 'corpus-analysis-concordance-exactly-n-character-modal' || modalId === 'corpus-analysis-concordance-between-nm-character-modal') {
-        button.addEventListener('click', () => this.tokenAttributeBuilderFunctions.characterNMSubmitHandler(modalId));
-      }
-    });
-
-    document.querySelector('#corpus-analysis-concordance-text-annotation-submit').addEventListener('click', () => this.structuralAttributeBuilderFunctions.textAnnotationSubmitHandler());
-
-    this.elements.positionalAttrModal = M.Modal.init(
-      document.querySelector('#corpus-analysis-concordance-positional-attr-modal'), 
-      {
-        onOpenStart: () => {
-          this.tokenAttributeBuilderFunctions.preparePositionalAttrModal();
-        },
-        onCloseStart: () => {
-          this.tokenAttributeBuilderFunctions.resetPositionalAttrModal();
-        }
-      }
-    );
-    this.elements.structuralAttrModal = M.Modal.init(
-      document.querySelector('#corpus-analysis-concordance-structural-attr-modal'), 
-      {
-        onCloseStart: () => {
-          this.structuralAttributeBuilderFunctions.resetStructuralAttrModal();
-        }
-      }
-    );
-  }
-}
diff --git a/app/static/js/CorpusAnalysis/QueryBuilder/ElementReferencesQueryBuilder.js b/app/static/js/CorpusAnalysis/query-builder/element-references.js
similarity index 100%
rename from app/static/js/CorpusAnalysis/QueryBuilder/ElementReferencesQueryBuilder.js
rename to app/static/js/CorpusAnalysis/query-builder/element-references.js
diff --git a/app/static/js/CorpusAnalysis/QueryBuilder/GeneralFunctionsQueryBuilder.js b/app/static/js/CorpusAnalysis/query-builder/general-query-builder-functions.js
similarity index 59%
rename from app/static/js/CorpusAnalysis/QueryBuilder/GeneralFunctionsQueryBuilder.js
rename to app/static/js/CorpusAnalysis/query-builder/general-query-builder-functions.js
index 7a25019943d5ac7b1b1da98b83fe21f7484cf51a..f1b04e74a83b4077f753b21031886414d51b0a6d 100644
--- a/app/static/js/CorpusAnalysis/QueryBuilder/GeneralFunctionsQueryBuilder.js
+++ b/app/static/js/CorpusAnalysis/query-builder/general-query-builder-functions.js
@@ -1,4 +1,4 @@
-class GeneralFunctionsQueryBuilder {
+class GeneralQueryBuilderFunctions {
   constructor(elements) {
     this.elements = elements;
   }
@@ -82,9 +82,10 @@ class GeneralFunctionsQueryBuilder {
         index = Array.from(this.elements.queryInputField.children).indexOf(closingTagElement);
       }
     }
-    if (index || isLastChildTextAnnotation) {
-      let insertingElement = isLastChildTextAnnotation ? lastChild : this.elements.queryChipElements[index];
-      this.elements.queryInputField.insertBefore(queryChipElement, insertingElement);
+    if (dataType !== 'text-annotation' && index) {
+      this.elements.queryInputField.insertBefore(queryChipElement, this.elements.queryChipElements[index]);
+    } else if (dataType !== 'text-annotation' && isLastChildTextAnnotation) {
+      this.elements.queryInputField.insertBefore(queryChipElement, lastChild);
     } else {
       this.elements.queryInputField.appendChild(queryChipElement);
     }
@@ -103,7 +104,8 @@ class GeneralFunctionsQueryBuilder {
       }
     });
     let chipActionButtons = queryChipElement.querySelectorAll('.chip-action-button');
-    chipActionButtons.forEach(button => {
+    // chipActionButtons.forEach(button => {
+    for (let button of chipActionButtons) {
       button.addEventListener('click', (event) => {
       if (event.target.dataset.chipAction === 'delete') {
         this.deleteChipElement(queryChipElement);
@@ -113,62 +115,22 @@ class GeneralFunctionsQueryBuilder {
         this.lockClosingChipElement(queryChipElement);
       }
       });
-    });
+    // });
+    }
   }
 
   editChipElement(queryChipElement) {
-    //TODO: Split this function into smaller functionss
     this.elements.editingModusOn = true;
     this.elements.editedQueryChipElementIndex = Array.from(this.elements.queryInputField.children).indexOf(queryChipElement);
     switch (queryChipElement.dataset.type) {
       case 'start-entity':
-        this.elements.structuralAttrModal.open();
-        this.toggleClass(['entity-builder'], 'hide', 'remove');
-        this.toggleEditingAreaStructureAttrModal('add');
-        let entType = queryChipElement.dataset.query.replace(/<ent_type="|">/g, '');
-        let isEnglishEntType = this.elements.englishEntTypeSelection.querySelector(`option[value=${entType}]`) !== null;
-        let selection = isEnglishEntType ? this.elements.englishEntTypeSelection : this.elements.germanEntTypeSelection;
-        this.resetMaterializeSelection([selection], entType);
+        this.editStartEntityChipElement(queryChipElement);
         break;
       case 'text-annotation':
-        this.elements.structuralAttrModal.open();
-        this.toggleClass(['text-annotation-builder'], 'hide', 'remove');
-        this.toggleEditingAreaStructureAttrModal('add');
-        let [textAnnotationSelection, textAnnotationContent] = queryChipElement.dataset.query
-          .replace(/:: ?match\.text_|"|"/g, '')
-          .split('=');
-        this.resetMaterializeSelection([this.elements.textAnnotationSelection], textAnnotationSelection);
-        this.elements.textAnnotationInput.value = textAnnotationContent;
+        this.editTextAnnotationChipElement(queryChipElement);
         break;
       case 'token':
-        //This regex searches for word or lemma or pos or simple_pos="any string within single or double quotes" followed by one or no ignore case markers, followed by one or no condition characters.
-      	let regex = new RegExp('(word|lemma|pos|simple_pos)=(("[^"]+")|(\\\\u0027[^\\\\u0027]+\\\\u0027)) ?(%c)? ?(\\&|\\|)?', 'gm');
-        let m;
-        let queryElementsContent = [];
-        while ((m = regex.exec(queryChipElement.dataset.query)) !== null) {
-          // This is necessary to avoid infinite loops with zero-width matches
-          if (m.index === regex.lastIndex) {
-              regex.lastIndex++;
-          }
-          let tokenAttr = m[1];
-          // Passes english-pos by default so that the template is added. In editTokenChipElement it is then checked whether it is english-pos or german-pos.
-          if (tokenAttr === 'pos') {
-            tokenAttr = 'english-pos';
-          }
-          let tokenValue = m[2].replace(/"|'/g, '');
-          let ignoreCase = false;
-          let condition = undefined;
-          m.forEach((match) => {
-            if (match === "%c") {
-              ignoreCase = true;
-            } else if (match === "&") {
-              condition = "and";
-            } else if (match === "|") {
-              condition = "or";
-            }
-          });
-          queryElementsContent.push({tokenAttr: tokenAttr, tokenValue: tokenValue, ignoreCase: ignoreCase, condition: condition});
-        }
+        let queryElementsContent = this.prepareQueryElementsContent(queryChipElement);
         this.editTokenChipElement(queryElementsContent);
         break;
       default:
@@ -176,6 +138,59 @@ class GeneralFunctionsQueryBuilder {
     }
   }
 
+  editStartEntityChipElement(queryChipElement) {
+    this.elements.structuralAttrModal.open();
+    this.toggleClass(['entity-builder'], 'hide', 'remove');
+    this.toggleEditingAreaStructuralAttrModal('add');
+    let entType = queryChipElement.dataset.query.replace(/<ent_type="|">/g, '');
+    let isEnglishEntType = this.elements.englishEntTypeSelection.querySelector(`option[value=${entType}]`) !== null;
+    let selection = isEnglishEntType ? this.elements.englishEntTypeSelection : this.elements.germanEntTypeSelection;
+    this.resetMaterializeSelection([selection], entType);
+  }
+
+  editTextAnnotationChipElement(queryChipElement) {
+    this.elements.structuralAttrModal.open();
+    this.toggleClass(['text-annotation-builder'], 'hide', 'remove');
+    this.structuralAttributeBuilderFunctions.toggleEditingAreaStructuralAttrModal('add');
+    let [textAnnotationSelection, textAnnotationContent] = queryChipElement.dataset.query
+      .replace(/:: ?match\.text_|"|"/g, '')
+      .split('=');
+    this.resetMaterializeSelection([this.elements.textAnnotationSelection], textAnnotationSelection);
+    this.elements.textAnnotationInput.value = textAnnotationContent;
+  }
+
+  prepareQueryElementsContent(queryChipElement) {
+    //this regex searches for word or lemma or pos or simple_pos="any string within single or double quotes" followed by one or no ignore case markers, followed by one or no condition characters.
+    let regex = new RegExp('(word|lemma|pos|simple_pos)=(("[^"]+")|(\\\\u0027[^\\\\u0027]+\\\\u0027)) ?(%c)? ?(\\&|\\|)?', 'gm');
+    let m;
+    let queryElementsContent = [];
+    while ((m = regex.exec(queryChipElement.dataset.query)) !== null) {
+      // this is necessary to avoid infinite loops with zero-width matches
+      if (m.index === regex.lastIndex) {
+          regex.lastIndex++;
+      }
+      let tokenAttr = m[1];
+      // Passes english-pos by default so that the template is added. In editTokenChipElement it is then checked whether it is english-pos or german-pos.
+      if (tokenAttr === 'pos') {
+        tokenAttr = 'english-pos';
+      }
+      let tokenValue = m[2].replace(/"|'/g, '');
+      let ignoreCase = false;
+      let condition = undefined;
+      m.forEach((match) => {
+        if (match === "%c") {
+          ignoreCase = true;
+        } else if (match === "&") {
+          condition = "and";
+        } else if (match === "|") {
+          condition = "or";
+        }
+      });
+      queryElementsContent.push({tokenAttr: tokenAttr, tokenValue: tokenValue, ignoreCase: ignoreCase, condition: condition});
+    }
+    return queryElementsContent;
+  }
+
   editTokenChipElement(queryElementsContent) {
     this.elements.positionalAttrModal.open();
     queryElementsContent.forEach((queryElement) => {
@@ -207,7 +222,6 @@ class GeneralFunctionsQueryBuilder {
       }
 
     });
-
   }
 
   lockClosingChipElement(queryChipElement) {
@@ -216,11 +230,6 @@ class GeneralFunctionsQueryBuilder {
     lockIcon.textContent = 'lock';
     //TODO: Write unlock-Function?
     lockIcon.dataset.chipAction = 'unlock';
-
-    // let chipIndex = Array.from(this.elements.queryInputField.children).indexOf(queryChipElement);
-    // this.submitQueryChipElement(queryChipElement.dataset.type, queryChipElement.firstChild.textContent, queryChipElement.dataset.query, chipIndex+1);
-    // this.deleteChipElement(queryChipElement);
-    // this.updateChipList();
   }
   
   deleteChipElement(attr) {
@@ -233,9 +242,8 @@ class GeneralFunctionsQueryBuilder {
         this.deletingClosingTagHandler(elementIndex, 'end-entity');
         break;
       case 'token':
-        console.log(Array.from(this.elements.queryInputField.children)[elementIndex+1]);
         let nextElement = Array.from(this.elements.queryInputField.children)[elementIndex+1];
-        if (nextElement.dataset.type === 'token-incidence-modifier') {
+        if (nextElement !== undefined && nextElement.dataset.type === 'token-incidence-modifier') {
           this.deleteChipElement(nextElement);
         }
       default:
@@ -264,16 +272,22 @@ class GeneralFunctionsQueryBuilder {
   handleDragStart(queryChipElement, event) {
     // is called when a query chip is dragged. It creates a dropzone (in form of a chip) for the dragged chip and adds it to the query input field.
     let queryChips = this.elements.queryInputField.querySelectorAll('.query-component');
+    if (queryChipElement.dataset.type === 'token-incidence-modifier') {
+      queryChips = this.elements.queryInputField.querySelectorAll('.query-component[data-type="token"]');
+    }
     setTimeout(() => {
       let targetChipElement = nopaque.Utils.HTMLToElement('<span class="chip drop-target">Drop here</span>');
       for (let element of queryChips) {
-        if (element === queryChipElement.nextSibling) {continue;}
-        let targetChipClone = targetChipElement.cloneNode(true);
-        if (element === queryChipElement && queryChips[queryChips.length - 1] !== element) {
-          queryChips[queryChips.length - 1].insertAdjacentElement('afterend', targetChipClone);
-        } else {
-          element.insertAdjacentElement('beforebegin', targetChipClone);
+        if (element === this.elements.queryInputField.querySelectorAll('.query-component')[0]) {
+          let secondTargetChipClone = targetChipElement.cloneNode(true);
+          element.insertAdjacentElement('beforebegin', secondTargetChipClone);
+          this.addDragDropListeners(secondTargetChipClone, queryChipElement);
         }
+        if (element === queryChipElement || element.nextSibling === queryChipElement) {continue;}
+
+        let targetChipClone = targetChipElement.cloneNode(true);
+        element.insertAdjacentElement('afterend', targetChipClone);
+
         this.addDragDropListeners(targetChipClone, queryChipElement);
       }
     }, 0);
@@ -371,135 +385,111 @@ class GeneralFunctionsQueryBuilder {
     this.tokenIncidenceModifierHandler(input, pretty_input);
   }
 
-  switchToExpertModeParser() {
-    let expertModeInputField = document.querySelector('#corpus-analysis-concordance-form-query');
-    expertModeInputField.value = '';
-    let queryBuilderInputFieldValue = nopaque.Utils.unescape(document.querySelector('#corpus-analysis-concordance-query-preview').innerHTML.trim());
-    if (queryBuilderInputFieldValue !== "" && queryBuilderInputFieldValue !== ";") {
-      expertModeInputField.value = queryBuilderInputFieldValue;
+  //#region Functions from other classes
+
+  //TODO: Move these functions back to their og classes and make it work.
+
+  toggleEditingAreaStructuralAttrModal(action) {
+    // If the user edits a query chip element, the corresponding editing area is displayed and the other areas are hidden or disabled.
+    this.toggleClass(['sentence-button', 'entity-button', 'text-annotation-button', 'any-type-entity-button'], 'disabled', action);
+  }
+
+  preparePositionalAttrModal() {
+    let selection = this.elements.positionalAttrSelection.value;
+    if (selection !== 'empty-token') {
+      let selectionTemplate = document.querySelector(`.token-builder-section[data-token-builder-section="${selection}"]`);
+      let selectionTemplateClone = selectionTemplate.content.cloneNode(true);
+    
+      this.elements.tokenBuilderContent.innerHTML = '';
+      this.elements.tokenBuilderContent.appendChild(selectionTemplateClone);
+      if (this.elements.tokenBuilderContent.querySelector('select') !== null) {
+        let selectElement = this.elements.tokenBuilderContent.querySelector('select');
+        M.FormSelect.init(selectElement);
+        selectElement.addEventListener('change', () => {this.optionToggleHandler();});
+      } else {
+        this.elements.tokenBuilderContent.querySelector('input').addEventListener('input', () => {this.optionToggleHandler();});
+      }
     }
+    this.optionToggleHandler();
+
+    if (selection === 'word' || selection === 'lemma') {
+      this.toggleClass(['input-field-options'], 'hide', 'remove');
+    } else if (selection === 'empty-token'){
+      this.addTokenToQuery();
+    } else {
+      this.toggleClass(['input-field-options'], 'hide', 'add');
+    }
+  }
+
+  tokenInputCheck(elem) {
+    return elem.querySelector('select') !== null ? elem.querySelector('select') : elem.querySelector('input');
   }
 
-  switchToQueryBuilderParser() {
-    this.resetQueryInputField();
-    let expertModeInputFieldValue = document.querySelector('#corpus-analysis-concordance-form-query').value;
-    let chipElements = this.parseTextToChip(expertModeInputFieldValue);
-    for (let chipElement of chipElements) {
-      this.submitQueryChipElement(chipElement['type'], chipElement['pretty'], chipElement['query']);
+  optionToggleHandler() {
+    let input = this.tokenInputCheck(this.elements.tokenBuilderContent);
+    if (input.value === '' && this.elements.editingModusOn === false) {
+      this.toggleClass(['incidence-modifiers', 'or', 'and'], 'disabled', 'add');
+    } else if (this.elements.positionalAttrSelection.querySelectorAll('option').length === 1) {
+      this.toggleClass(['and'], 'disabled', 'add');
+      this.toggleClass(['or'], 'disabled', 'remove');
+    } else {
+      this.toggleClass(['incidence-modifiers', 'or', 'and'], 'disabled', 'remove');
     }
   }
 
-  parseTextToChip(query) {
-    const parsingElementDict = {
-      '<s>': {
-        pretty: 'Sentence Start',
-        type: 'start-sentence'
-      },
-      '<\/s>': {
-        pretty: 'Sentence End',
-        type: 'end-sentence'
-      },
-      '<ent>': {
-        pretty: 'Entity Start',
-        type: 'start-empty-entity'
-      },
-      '<ent_type="([A-Z]+)">': {
-        pretty: '',
-        type: 'start-entity'
-      },
-      '<\\\/ent(_type)?>': {
-        pretty: 'Entity End',
-        type: 'end-entity'
-      },
-      ':: ?match\\.text_[A-Za-z]+="[^"]+"': {
-        pretty: '',
-        type: 'text-annotation'
-      },
-      '\\[(word|lemma|pos|simple_pos)=(("[^"]+")|(\\u0027[^\\u0027]+\\u0027)) ?(%c)? ?((\\&|\\|) ?(word|lemma|pos|simple_pos)=(("[^"]+")|(\\u0027[^\\u0027]+\\u0027)) ?(%c)? ?)*\\]': {
-        pretty: '',
-        type: 'token'
-      },
-      '\\[\\]': {
-        pretty: 'Empty Token',
-        type: 'token'
-      },
-      '(?<!\\[) ?\\+ ?(?![^\\]]\\])': {
-        pretty: ' one or more (+)',
-        type: 'token-incidence-modifier'
-      },
-      '(?<!\\[) ?\\* ?(?![^\\]]\\])': {
-        pretty: 'zero or more (*)',
-        type: 'token-incidence-modifier'
-      },
-      '(?<!\\[) ?\\? ?(?![^\\]]\\])': {
-        pretty: 'zero or one (?)',
-        type: 'token-incidence-modifier'
-      },
-      '(?<!\\[) ?\\{[0-9]+} ?(?![^\\]]\\])': {
-        pretty: '',
-        type: 'token-incidence-modifier'
-      },
-      '(?<!\\[) ?\\{[0-9]+(,[0-9]+)?} ?(?![^\\]]\\])': {
-        pretty: '',
-        type: 'token-incidence-modifier'
-      }
+  addTokenToQuery() {
+    let tokenQueryPrettyText = '';
+    let tokenQueryCQLText = '';
+    let input;
+    let kindOfToken = this.kindOfTokenCheck(this.elements.positionalAttrSelection.value);
+    
+    // Takes all rows of the token query (if there is a query concatenation).
+    // Adds their contents to tokenQueryPrettyText and tokenQueryCQLText, which will later be expanded with the current input field.
+    let tokenQueryRows = this.elements.tokenQuery.querySelectorAll('.row');
+    tokenQueryRows.forEach(row => {
+      let ignoreCaseCheckbox = row.querySelector('input[type="checkbox"]');
+      let c = ignoreCaseCheckbox !== null && ignoreCaseCheckbox.checked ? ' %c' : '';
+      let tokenQueryRowInput = this.tokenInputCheck(row.querySelector('.token-query-template-content'));
+      let tokenQueryKindOfToken = this.kindOfTokenCheck(tokenQueryRowInput.closest('.input-field').dataset.kindOfToken);
+      let tokenConditionPrettyText = row.querySelector('[data-condition-pretty-text]').dataset.conditionPrettyText;
+      let tokenConditionCQLText = row.querySelector('[data-condition-cql-text]').dataset.conditionCqlText;
+      tokenQueryPrettyText += `${tokenQueryKindOfToken}=${tokenQueryRowInput.value}${c} ${tokenConditionPrettyText} `;
+      tokenQueryCQLText += `${tokenQueryKindOfToken}="${tokenQueryRowInput.value}"${c} ${tokenConditionCQLText}`;
+    });
+    if (kindOfToken === 'empty-token') {
+      tokenQueryPrettyText += 'empty token';
+    } else {
+      let c = this.elements.ignoreCaseCheckbox.checked ? ' %c' : '';
+      input = this.tokenInputCheck(this.elements.tokenBuilderContent);
+      tokenQueryPrettyText += `${kindOfToken}=${input.value}${c}`;
+      tokenQueryCQLText += `${kindOfToken}="${input.value}"${c}`;
     }
-  
-    let chipElements = [];
-    let regexPattern = Object.keys(parsingElementDict).map(pattern => `(${pattern})`).join('|');
-    const regex = new RegExp(regexPattern, 'gi');
-    let match;
-  
-    while ((match = regex.exec(query)) !== null) {
-      // This is necessary to avoid infinite loops with zero-width matches
-      if (match.index === regex.lastIndex) {
-        regex.lastIndex++;
-      }
-      let stringElement = match[0];
-      for (let [pattern, chipElement] of Object.entries(parsingElementDict)) {
-        const parsingRegex = new RegExp(pattern, 'gi');
-        if (parsingRegex.exec(stringElement)) {
-          // Creating the pretty text for the chip element
-          let prettyText;
-          switch (pattern) {
-            case '<ent_type="([A-Z]+)">':
-              prettyText = `Entity Type=${stringElement.replace(/<ent_type="|">/g, '')}`;
-              break;
-            case ':: ?match\\.text_[A-Za-z]+="[^"]+"':
-              prettyText = stringElement.replace(/:: ?match\.text_|"|"/g, '');
-              break;
-            case '\\[(word|lemma|pos|simple_pos)=(("[^"]+")|(\\u0027[^\\u0027]+\\u0027)) ?(%c)? ?((\\&|\\|) ?(word|lemma|pos|simple_pos)=(("[^"]+")|(\\u0027[^\\u0027]+\\u0027)) ?(%c)? ?)*\\]':
-              let doubleQuotes = /(word|lemma|pos|simple_pos)="[^"]+"/gi;
-              let singleQuotes = /(word|lemma|pos|simple_pos)='[^']+'/gi;
-              if (doubleQuotes.exec(stringElement)) {
-                prettyText = stringElement.replace(/^\[|\]$|"/g, '');
-              } else if (singleQuotes.exec(stringElement)) {
-                prettyText = stringElement.replace(/^\[|\]$|'/g, '');
-              }
-              prettyText = prettyText.replace(/\&/g, ' and ').replace(/\|/g, ' or ');
-              break;
-            case '(?<!\\[) ?\\{[0-9]+} ?(?![^\\]]\\])':
-              prettyText = `exactly ${stringElement.replace(/{|}/g, '')} (${stringElement})`;
-              break;
-            case '(?<!\\[) ?\\{[0-9]+(,[0-9]+)?} ?(?![^\\]]\\])':
-              prettyText = `between${stringElement.replace(/{|}/g, ' ').replace(',', ' and ')}(${stringElement})`;
-              break;
-            default:
-              prettyText = chipElement.pretty;
-              break;
-          }
-          chipElements.push({
-            type: chipElement.type,
-            pretty: prettyText,
-            query: stringElement
-          });
-          break;
-        }
-      }
+    // isTokenQueryInvalid looks if a valid value is passed. If the input fields/dropdowns are empty (isTokenQueryInvalid === true), no token is added.
+    if (this.elements.positionalAttrSelection.value !== 'empty-token' && input.value === '') {
+      this.disableTokenSubmit();
+    } else {
+      tokenQueryCQLText = `[${tokenQueryCQLText}]`;
+      this.submitQueryChipElement('token', tokenQueryPrettyText, tokenQueryCQLText, null, false, kindOfToken === 'empty-token' ? false : true);
+      this.elements.positionalAttrModal.close();
     }
+  }
   
-    return chipElements;
+  kindOfTokenCheck(kindOfToken) {
+    return kindOfToken === 'english-pos' || kindOfToken === 'german-pos' ? 'pos' : kindOfToken;
+  }
+
+  disableTokenSubmit() {
+    this.elements.tokenSubmitButton.classList.add('red');
+    this.elements.noValueMessage.classList.remove('hide');
+    setTimeout(() => {
+      this.elements.tokenSubmitButton.classList.remove('red');
+    }, 500);
+    setTimeout(() => {
+      this.elements.noValueMessage.classList.add('hide');
+    }, 3000);
   }
 
+  //#endregion Functions from other classes
+
 }
 
diff --git a/app/static/js/CorpusAnalysis/query-builder/index.js b/app/static/js/CorpusAnalysis/query-builder/index.js
new file mode 100644
index 0000000000000000000000000000000000000000..5050c09f5350036ba72ee4c45fbf490dfb883d23
--- /dev/null
+++ b/app/static/js/CorpusAnalysis/query-builder/index.js
@@ -0,0 +1,192 @@
+class ConcordanceQueryBuilder {
+
+  constructor() {
+    this.elements = new ElementReferencesQueryBuilder();
+    this.generalFunctions = new GeneralQueryBuilderFunctions(this.elements);
+    this.tokenAttributeBuilderFunctions = new TokenAttributeBuilderFunctions(this.elements);
+    this.structuralAttributeBuilderFunctions = new StructuralAttributeBuilderFunctions(this.elements);
+
+    this.incidenceModifierEventListeners();
+    this.nAndMInputSubmitEventListeners();
+
+    let queryBuilderDisplay = document.querySelector("#corpus-analysis-concordance-query-builder-display");
+    let expertModeDisplay = document.querySelector("#corpus-analysis-concordance-expert-mode-display");
+    let expertModeSwitch = document.querySelector("#corpus-analysis-concordance-expert-mode-switch");
+    
+    expertModeSwitch.addEventListener("change", () => {
+      const isChecked = expertModeSwitch.checked;
+      if (isChecked) {
+        queryBuilderDisplay.classList.add("hide");
+        expertModeDisplay.classList.remove("hide");
+        this.switchToExpertModeParser();
+      } else {
+        queryBuilderDisplay.classList.remove("hide");
+        expertModeDisplay.classList.add("hide");
+        this.switchToQueryBuilderParser();
+      }
+    });
+    
+  }
+
+  incidenceModifierEventListeners() {
+    // Eventlisteners for the incidence modifiers. There are two different types of incidence modifiers: token and character incidence modifiers.
+    document.querySelectorAll('.incidence-modifier-selection').forEach(button => {
+      let dropdownId = button.parentNode.parentNode.id;
+      if (dropdownId === 'corpus-analysis-concordance-token-incidence-modifiers-dropdown') {
+        button.addEventListener('click', () => this.generalFunctions.tokenIncidenceModifierHandler(button.dataset.token, button.innerHTML));
+      } else if (dropdownId === 'corpus-analysis-concordance-character-incidence-modifiers-dropdown') {
+        button.addEventListener('click', () => this.tokenAttributeBuilderFunctions.characterIncidenceModifierHandler(button));
+      }
+    });
+  }
+
+  nAndMInputSubmitEventListeners() {
+    // Eventlisteners for the submit of n- and m-values of the incidence modifier modal for "exactly n" or "between n and m".
+    document.querySelectorAll('.n-m-submit-button').forEach(button => {
+      let modalId = button.dataset.modalId;
+      if (modalId === 'corpus-analysis-concordance-exactly-n-token-modal' || modalId === 'corpus-analysis-concordance-between-nm-token-modal') {
+        button.addEventListener('click', () => this.generalFunctions.tokenNMSubmitHandler(modalId));
+      } else if (modalId === 'corpus-analysis-concordance-exactly-n-character-modal' || modalId === 'corpus-analysis-concordance-between-nm-character-modal') {
+        button.addEventListener('click', () => this.tokenAttributeBuilderFunctions.characterNMSubmitHandler(modalId));
+      }
+    });
+  }
+
+  switchToExpertModeParser() {
+    let expertModeInputField = document.querySelector('#corpus-analysis-concordance-form-query');
+    expertModeInputField.value = '';
+    let queryBuilderInputFieldValue = Utils.unescape(document.querySelector('#corpus-analysis-concordance-query-preview').innerHTML.trim());
+    if (queryBuilderInputFieldValue !== "" && queryBuilderInputFieldValue !== ";") {
+      expertModeInputField.value = queryBuilderInputFieldValue;
+    }
+  }
+
+  switchToQueryBuilderParser() {
+    this.generalFunctions.resetQueryInputField();
+    let expertModeInputFieldValue = document.querySelector('#corpus-analysis-concordance-form-query').value;
+    let chipElements = this.parseTextToChip(expertModeInputFieldValue);
+    let closingTagElements = ['end-sentence', 'end-entity'];
+    let editableElements = ['start-entity', 'text-annotation', 'token'];
+    for (let chipElement of chipElements) {
+      let isClosingTag = closingTagElements.includes(chipElement['type']);
+      let isEditable = editableElements.includes(chipElement['type']);
+      if (chipElement['query'] === '[]'){
+        isEditable = false;
+      }
+      this.generalFunctions.submitQueryChipElement(chipElement['type'], chipElement['pretty'], chipElement['query'], null, isClosingTag, isEditable);
+    }
+  }
+
+  parseTextToChip(query) {
+    const parsingElementDict = {
+      '<s>': {
+        pretty: 'Sentence Start',
+        type: 'start-sentence'
+      },
+      '<\/s>': {
+        pretty: 'Sentence End',
+        type: 'end-sentence'
+      },
+      '<ent>': {
+        pretty: 'Entity Start',
+        type: 'start-empty-entity'
+      },
+      '<ent_type="([A-Z]+)">': {
+        pretty: '',
+        type: 'start-entity'
+      },
+      '<\\\/ent(_type)?>': {
+        pretty: 'Entity End',
+        type: 'end-entity'
+      },
+      ':: ?match\\.text_[A-Za-z]+="[^"]+"': {
+        pretty: '',
+        type: 'text-annotation'
+      },
+      '\\[(word|lemma|pos|simple_pos)=(("[^"]+")|(\\u0027[^\\u0027]+\\u0027)) ?(%c)? ?((\\&|\\|) ?(word|lemma|pos|simple_pos)=(("[^"]+")|(\\u0027[^\\u0027]+\\u0027)) ?(%c)? ?)*\\]': {
+        pretty: '',
+        type: 'token'
+      },
+      '\\[\\]': {
+        pretty: 'Empty Token',
+        type: 'token'
+      },
+      '(?<!\\[) ?\\+ ?(?![^\\]]\\])': {
+        pretty: ' one or more (+)',
+        type: 'token-incidence-modifier'
+      },
+      '(?<!\\[) ?\\* ?(?![^\\]]\\])': {
+        pretty: 'zero or more (*)',
+        type: 'token-incidence-modifier'
+      },
+      '(?<!\\[) ?\\? ?(?![^\\]]\\])': {
+        pretty: 'zero or one (?)',
+        type: 'token-incidence-modifier'
+      },
+      '(?<!\\[) ?\\{[0-9]+} ?(?![^\\]]\\])': {
+        pretty: '',
+        type: 'token-incidence-modifier'
+      },
+      '(?<!\\[) ?\\{[0-9]+(,[0-9]+)?} ?(?![^\\]]\\])': {
+        pretty: '',
+        type: 'token-incidence-modifier'
+      }
+    }
+  
+    let chipElements = [];
+    let regexPattern = Object.keys(parsingElementDict).map(pattern => `(${pattern})`).join('|');
+    const regex = new RegExp(regexPattern, 'gi');
+    let match;
+  
+    while ((match = regex.exec(query)) !== null) {
+      // this is necessary to avoid infinite loops with zero-width matches
+      if (match.index === regex.lastIndex) {
+        regex.lastIndex++;
+      }
+      let stringElement = match[0];
+      for (let [pattern, chipElement] of Object.entries(parsingElementDict)) {
+        const parsingRegex = new RegExp(pattern, 'gi');
+        if (parsingRegex.exec(stringElement)) {
+          // Creating the pretty text for the chip element
+          let prettyText;
+          switch (pattern) {
+            case '<ent_type="([A-Z]+)">':
+              prettyText = `Entity Type=${stringElement.replace(/<ent_type="|">/g, '')}`;
+              break;
+            case ':: ?match\\.text_[A-Za-z]+="[^"]+"':
+              prettyText = stringElement.replace(/:: ?match\.text_|"|"/g, '');
+              break;
+            case '\\[(word|lemma|pos|simple_pos)=(("[^"]+")|(\\u0027[^\\u0027]+\\u0027)) ?(%c)? ?((\\&|\\|) ?(word|lemma|pos|simple_pos)=(("[^"]+")|(\\u0027[^\\u0027]+\\u0027)) ?(%c)? ?)*\\]':
+              let doubleQuotes = /(word|lemma|pos|simple_pos)="[^"]+"/gi;
+              let singleQuotes = /(word|lemma|pos|simple_pos)='[^']+'/gi;
+              if (doubleQuotes.exec(stringElement)) {
+                prettyText = stringElement.replace(/^\[|\]$|"/g, '');
+              } else if (singleQuotes.exec(stringElement)) {
+                prettyText = stringElement.replace(/^\[|\]$|'/g, '');
+              }
+              prettyText = prettyText.replace(/\&/g, ' and ').replace(/\|/g, ' or ');
+              break;
+            case '(?<!\\[) ?\\{[0-9]+} ?(?![^\\]]\\])':
+              prettyText = `exactly ${stringElement.replace(/{|}/g, '')} (${stringElement})`;
+              break;
+            case '(?<!\\[) ?\\{[0-9]+(,[0-9]+)?} ?(?![^\\]]\\])':
+              prettyText = `between${stringElement.replace(/{|}/g, ' ').replace(',', ' and ')}(${stringElement})`;
+              break;
+            default:
+              prettyText = chipElement.pretty;
+              break;
+          }
+          chipElements.push({
+            type: chipElement.type,
+            pretty: prettyText,
+            query: stringElement
+          });
+          break;
+        }
+      }
+    }
+  
+    return chipElements;
+  }
+  
+}
diff --git a/app/static/js/CorpusAnalysis/QueryBuilder/StructuralAttributeBuilderFunctionsQueryBuilder.js b/app/static/js/CorpusAnalysis/query-builder/structural-attribute-builder-functions.js
similarity index 86%
rename from app/static/js/CorpusAnalysis/QueryBuilder/StructuralAttributeBuilderFunctionsQueryBuilder.js
rename to app/static/js/CorpusAnalysis/query-builder/structural-attribute-builder-functions.js
index d8f9fbe9c0ad26b202a0feb8130cef35ccd2c8ae..8802686624e7c4e5062cbeb95ddfc45f9d7efb2b 100644
--- a/app/static/js/CorpusAnalysis/QueryBuilder/StructuralAttributeBuilderFunctionsQueryBuilder.js
+++ b/app/static/js/CorpusAnalysis/query-builder/structural-attribute-builder-functions.js
@@ -1,8 +1,22 @@
-class StructuralAttributeBuilderFunctionsQueryBuilder extends GeneralFunctionsQueryBuilder {
+class StructuralAttributeBuilderFunctions extends GeneralQueryBuilderFunctions {
   constructor(elements) {
     super(elements);
-    this.elements = elements;
 
+    this.structuralAttrModalEventlisteners();
+
+    document.querySelector('#corpus-analysis-concordance-text-annotation-submit').addEventListener('click', () => this.textAnnotationSubmitHandler());
+
+    this.elements.structuralAttrModal = M.Modal.init(
+      document.querySelector('#corpus-analysis-concordance-structural-attr-modal'), 
+      {
+        onCloseStart: () => {
+          this.resetStructuralAttrModal();
+        }
+      }
+    );
+  }
+
+  structuralAttrModalEventlisteners() {
     document.querySelectorAll('[data-structural-attr-modal-action-button]').forEach(button => {
       button.addEventListener('click', () => {
         this.actionButtonInStrucAttrModalHandler(button.dataset.structuralAttrModalActionButton);
@@ -35,16 +49,11 @@ class StructuralAttributeBuilderFunctionsQueryBuilder extends GeneralFunctionsQu
     this.elements.textAnnotationInput.value = '';
 
     this.toggleClass(['entity-builder', 'text-annotation-builder'], 'hide', 'add');
-    this.toggleEditingAreaStructureAttrModal('remove');
+    this.toggleEditingAreaStructuralAttrModal('remove');
     this.elements.editingModusOn = false;
     this.elements.editedQueryChipElementIndex = undefined;
   }
 
-  toggleEditingAreaStructureAttrModal(action) {
-    // If the user edits a query chip element, the corresponding editing area is displayed and the other areas are hidden or disabled.
-    this.toggleClass(['sentence-button', 'entity-button', 'text-annotation-button', 'any-type-entity-button'], 'disabled', action);
-  }
-
   actionButtonInStrucAttrModalHandler(action) {
     switch (action) {
       case 'sentence':
diff --git a/app/static/js/CorpusAnalysis/QueryBuilder/TokenAttributeBuilderFunctionsQueryBuilder.js b/app/static/js/CorpusAnalysis/query-builder/token-attribute-builder-functions.js
similarity index 59%
rename from app/static/js/CorpusAnalysis/QueryBuilder/TokenAttributeBuilderFunctionsQueryBuilder.js
rename to app/static/js/CorpusAnalysis/query-builder/token-attribute-builder-functions.js
index bebb5d83dac29f163c2626d80fd42a1f578b62e7..d3dbe55c004246675b41d27b59b0f65ee5bf5da4 100644
--- a/app/static/js/CorpusAnalysis/QueryBuilder/TokenAttributeBuilderFunctionsQueryBuilder.js
+++ b/app/static/js/CorpusAnalysis/query-builder/token-attribute-builder-functions.js
@@ -1,7 +1,6 @@
-class TokenAttributeBuilderFunctionsQueryBuilder extends GeneralFunctionsQueryBuilder {
+class TokenAttributeBuilderFunctions extends GeneralQueryBuilderFunctions {
   constructor(elements) {
     super(elements);
-    this.elements = elements;
 
     this.elements.positionalAttrSelection.addEventListener('change', () => {
       this.preparePositionalAttrModal();
@@ -13,6 +12,18 @@ class TokenAttributeBuilderFunctionsQueryBuilder extends GeneralFunctionsQueryBu
     });
 
     this.elements.tokenSubmitButton.addEventListener('click', () => {this.addTokenToQuery();});
+
+    this.elements.positionalAttrModal = M.Modal.init(
+      document.querySelector('#corpus-analysis-concordance-positional-attr-modal'), 
+      {
+        onOpenStart: () => {
+          this.preparePositionalAttrModal();
+        },
+        onCloseStart: () => {
+          this.resetPositionalAttrModal();
+        }
+      }
+    );
   }
 
   resetPositionalAttrModal() {
@@ -35,100 +46,6 @@ class TokenAttributeBuilderFunctionsQueryBuilder extends GeneralFunctionsQueryBu
     this.elements.editingModusOn = false;
     this.elements.editedQueryChipElementIndex = undefined;
   }
-  
-  preparePositionalAttrModal() {
-    let selection = this.elements.positionalAttrSelection.value;
-    if (selection !== 'empty-token') {
-      let selectionTemplate = document.querySelector(`.token-builder-section[data-token-builder-section="${selection}"]`);
-      let selectionTemplateClone = selectionTemplate.content.cloneNode(true);
-    
-      this.elements.tokenBuilderContent.innerHTML = '';
-      this.elements.tokenBuilderContent.appendChild(selectionTemplateClone);
-      if (this.elements.tokenBuilderContent.querySelector('select') !== null) {
-        let selectElement = this.elements.tokenBuilderContent.querySelector('select');
-        M.FormSelect.init(selectElement);
-        selectElement.addEventListener('change', () => {this.optionToggleHandler();});
-      } else {
-        this.elements.tokenBuilderContent.querySelector('input').addEventListener('input', () => {this.optionToggleHandler();});
-      }
-    }
-    this.optionToggleHandler();
-
-    if (selection === 'word' || selection === 'lemma') {
-      this.toggleClass(['input-field-options'], 'hide', 'remove');
-    } else if (selection === 'empty-token'){
-      this.addTokenToQuery();
-    } else {
-      this.toggleClass(['input-field-options'], 'hide', 'add');
-    }
-  }
-
-  tokenInputCheck(elem) {
-    return elem.querySelector('select') !== null ? elem.querySelector('select') : elem.querySelector('input');
-  }
-
-  optionToggleHandler() {
-    let input = this.tokenInputCheck(this.elements.tokenBuilderContent);
-    if (input.value === '' && this.elements.editingModusOn === false) {
-      this.toggleClass(['incidence-modifiers', 'or', 'and'], 'disabled', 'add');
-    } else if (this.elements.positionalAttrSelection.querySelectorAll('option').length === 1) {
-      this.toggleClass(['and'], 'disabled', 'add');
-    } else {
-      this.toggleClass(['incidence-modifiers', 'or', 'and'], 'disabled', 'remove');
-    }
-  }
-
-  disableTokenSubmit() {
-    this.elements.tokenSubmitButton.classList.add('red');
-    this.elements.noValueMessage.classList.remove('hide');
-    setTimeout(() => {
-      this.elements.tokenSubmitButton.classList.remove('red');
-    }, 500);
-    setTimeout(() => {
-      this.elements.noValueMessage.classList.add('hide');
-    }, 3000);
-  }
-
-  addTokenToQuery() {
-    let tokenQueryPrettyText = '';
-    let tokenQueryCQLText = '';
-    let input;
-    let kindOfToken = this.kindOfTokenCheck(this.elements.positionalAttrSelection.value);
-    
-    // Takes all rows of the token query (if there is a query concatenation).
-    // Adds their contents to tokenQueryPrettyText and tokenQueryCQLText, which will later be expanded with the current input field.
-    let tokenQueryRows = this.elements.tokenQuery.querySelectorAll('.row');
-    tokenQueryRows.forEach(row => {
-      let ignoreCaseCheckbox = row.querySelector('input[type="checkbox"]');
-      let c = ignoreCaseCheckbox !== null && ignoreCaseCheckbox.checked ? ' %c' : '';
-      let tokenQueryRowInput = this.tokenInputCheck(row.querySelector('.token-query-template-content'));
-      let tokenQueryKindOfToken = this.kindOfTokenCheck(tokenQueryRowInput.closest('.input-field').dataset.kindOfToken);
-      let tokenConditionPrettyText = row.querySelector('[data-condition-pretty-text]').dataset.conditionPrettyText;
-      let tokenConditionCQLText = row.querySelector('[data-condition-cql-text]').dataset.conditionCqlText;
-      tokenQueryPrettyText += `${tokenQueryKindOfToken}=${tokenQueryRowInput.value}${c} ${tokenConditionPrettyText} `;
-      tokenQueryCQLText += `${tokenQueryKindOfToken}="${tokenQueryRowInput.value}"${c} ${tokenConditionCQLText}`;
-    });
-    if (kindOfToken === 'empty-token') {
-      tokenQueryPrettyText += 'empty token';
-    } else {
-      let c = this.elements.ignoreCaseCheckbox.checked ? ' %c' : '';
-      input = this.tokenInputCheck(this.elements.tokenBuilderContent);
-      tokenQueryPrettyText += `${kindOfToken}=${input.value}${c}`;
-      tokenQueryCQLText += `${kindOfToken}="${input.value}"${c}`;
-    }
-    // isTokenQueryInvalid looks if a valid value is passed. If the input fields/dropdowns are empty (isTokenQueryInvalid === true), no token is added.
-    if (this.elements.positionalAttrSelection.value !== 'empty-token' && input.value === '') {
-      this.disableTokenSubmit();
-    } else {
-      tokenQueryCQLText = `[${tokenQueryCQLText}]`;
-      this.submitQueryChipElement('token', tokenQueryPrettyText, tokenQueryCQLText, null, false, kindOfToken === 'empty-token' ? false : true);
-      this.elements.positionalAttrModal.close();
-    }
-  }
-
-  kindOfTokenCheck(kindOfToken) {
-    return kindOfToken === 'english-pos' || kindOfToken === 'german-pos' ? 'pos' : kindOfToken;
-  }
 
   actionButtonInOptionSectionHandler(elem) {
     let input = this.tokenInputCheck(this.elements.tokenBuilderContent);
@@ -173,7 +90,7 @@ class TokenAttributeBuilderFunctionsQueryBuilder extends GeneralFunctionsQueryBu
     tokenInput.value += '{' + input + '}';
   }
 
-  conditionHandler(conditionText, editMode = false) {
+  conditionHandler(conditionText) {
     let tokenQueryTemplateClone = this.elements.tokenQueryTemplate.content.cloneNode(true);
     tokenQueryTemplateClone.querySelector('.token-query-template-content').appendChild(this.elements.tokenBuilderContent.firstElementChild);
     let notSelectedButton = tokenQueryTemplateClone.querySelector(`[data-condition-pretty-text]:not([data-condition-pretty-text="${conditionText}"])`);
@@ -261,4 +178,5 @@ class TokenAttributeBuilderFunctionsQueryBuilder extends GeneralFunctionsQueryBu
     this.resetMaterializeSelection([this.elements.positionalAttrSelection], selection);
     this.preparePositionalAttrModal();
   }
+
 }
diff --git a/app/templates/_scripts.html.j2 b/app/templates/_scripts.html.j2
index b4f362a44af7654bea216cf4725f2cdb3f49d644..152409d37160111ac4d9670b3a5a794631d53bc3 100644
--- a/app/templates/_scripts.html.j2
+++ b/app/templates/_scripts.html.j2
@@ -95,13 +95,13 @@
 {%- assets
   filters='rjsmin',
   output='gen/CorpusAnalysis.%(version)s.js',
-  'js/CorpusAnalysis/QueryBuilder/ElementReferencesQueryBuilder.js',
-  'js/CorpusAnalysis/QueryBuilder/GeneralFunctionsQueryBuilder.js',
-  'js/CorpusAnalysis/QueryBuilder/StructuralAttributeBuilderFunctionsQueryBuilder.js',
-  'js/CorpusAnalysis/QueryBuilder/TokenAttributeBuilderFunctionsQueryBuilder.js',
+  'js/CorpusAnalysis/query-builder/index.js',
+  'js/CorpusAnalysis/query-builder/element-references.js',
+  'js/CorpusAnalysis/query-builder/general-query-builder-functions.js',
+  'js/CorpusAnalysis/query-builder/structural-attribute-builder-functions.js',
+  'js/CorpusAnalysis/query-builder/token-attribute-builder-functions.js',
   'js/CorpusAnalysis/CorpusAnalysisApp.js',
   'js/CorpusAnalysis/CorpusAnalysisConcordance.js',
-  'js/CorpusAnalysis/QueryBuilder.js',
   'js/CorpusAnalysis/CorpusAnalysisReader.js',
   'js/CorpusAnalysis/CorpusAnalysisStaticVisualization.js'
 %}
diff --git a/app/templates/corpora/_analysis/concordance.html.j2 b/app/templates/corpora/_analysis/concordance.html.j2
index b160c2fb5f2d708ee35bd7aaa1f4740c45a1b212..f50578bdf05f989fed1b475219f03031bd4a80a1 100644
--- a/app/templates/corpora/_analysis/concordance.html.j2
+++ b/app/templates/corpora/_analysis/concordance.html.j2
@@ -130,21 +130,5 @@
 <script>
   const corpusAnalysisConcordance = new CorpusAnalysisConcordance(corpusAnalysisApp);
   const concordanceQueryBuilder = new ConcordanceQueryBuilder();
-
-  let queryBuilderDisplay = document.getElementById("corpus-analysis-concordance-query-builder-display");
-  let expertModeDisplay = document.getElementById("corpus-analysis-concordance-expert-mode-display");
-  let expertModeSwitch = document.getElementById("corpus-analysis-concordance-expert-mode-switch");
-
-  expertModeSwitch.addEventListener("change", function() {
-    if (this.checked) {
-      queryBuilderDisplay.classList.add("hide");
-      expertModeDisplay.classList.remove("hide");
-      concordanceQueryBuilder.generalFunctions.switchToExpertModeParser();
-    } else {
-      queryBuilderDisplay.classList.remove("hide");
-      expertModeDisplay.classList.add("hide");
-      concordanceQueryBuilder.generalFunctions.switchToQueryBuilderParser();
-    }
-  });
 </script>
 {% endmacro %}