From 0c5ace522c2c4e32b398da859fb2bae00c93f281 Mon Sep 17 00:00:00 2001 From: David Tran Duc Date: Wed, 16 Sep 2020 00:26:03 +0200 Subject: [PATCH] WIP --- app/frontend/helpers/dynamicTextFormater.ts | 57 ++++++++++----------- 1 file changed, 26 insertions(+), 31 deletions(-) diff --git a/app/frontend/helpers/dynamicTextFormater.ts b/app/frontend/helpers/dynamicTextFormater.ts index 339e43f853..60f5853f95 100644 --- a/app/frontend/helpers/dynamicTextFormater.ts +++ b/app/frontend/helpers/dynamicTextFormater.ts @@ -2,41 +2,35 @@ import {isBip39Word} from '../wallet/mnemonic' import {getCaretPosition, setCaretPosition} from './caretPosition' import matchAll from './matchAll' -const underlineNonBip39words = (element, /*component*/ content) => { +const underlineNonBip39words = (element, content) => { const innerHTML = element.innerHTML if (content !== innerHTML) { const caretPosition = getCaretPosition(element) let toFormat = innerHTML // 1. forbid multiple divs (lines) - // console.log('========================================') - // console.log(`0. ${toFormat}`) toFormat = toFormat.replace(/<\/{0,1}(div|br|p)[^<>]*>/g, '') - // console.log(`1. ${toFormat}`) // 2. only non-breaking space allowed as whitespace toFormat = toFormat.replace(/\s| /g, ' ') - // console.log(`2. ${toFormat}`) // 3. wrap span around words at the start of line - // (^[^<>a-zA-Z]*) - find start of line and absence of '<' and '>' - // [a-zA-Z]+ - find word itself - // ((\s|[,;])+a-zA-Z]* - find start of line and absence of '<' and '>' + // [a-zA-Z]+ - find word itself + // (\s|[,;])+a-zA-Z]*)([a-zA-Z]+)((\s|[,;])+$2$3' ) - // console.log(`3. ${toFormat}`) // 4. wrap span around words in the middle of line - // (<\/span>(\s|[,;])+) - find '' before word - // [a-zA-Z]+ - find word itself - // ((\s|[,;])+(\s|[,;])+ - find '' before word + // [a-zA-Z]+ - find word itself + // (\s|[,;])+(\s|[,;])+)([a-zA-Z]+)((\s|[,;])+$2$3' + '$1$3$4' ) - // console.log(`4. ${toFormat}`) // 5. wrap span around words in the end of the line // (?<=^|\s|[,;]) - check for delimiter before word @@ -48,7 +42,6 @@ const underlineNonBip39words = (element, /*component*/ content) => { /(?<=^|\s|[,;])[a-zA-Z]+(?=$|\s|[,;])(?=[^<>]*$)/g, '$&' ) - // console.log(`5. ${toFormat}`) // 6. split words by whitespace or commas // (? { // (\s|[,;])+ - find whitespaces or commas // (?!\s|[<,;]) - check for '<' symbol from next span tag toFormat = toFormat.replace(/(?,;]|\s)(\s|[,;])+(?!\s|[<,;])/g, '$&') - // console.log(`6. ${toFormat}`) // 7. merge words if there is no whitespace between them toFormat = toFormat.replace(/<\/span>]*>/g, '') - // console.log(`7. ${toFormat}`) // 8. append to wrapped word // ]*> - find opening tag before word // [a-zA-Z]+ - find word itself // <\/span> - find closing tag after word - // ([a-zA-Z]+) - find text to append + // [a-zA-Z]+ - find text to append toFormat = toFormat.replace(/(]*>[a-zA-Z]+)(<\/span>)([a-zA-Z]+)/g, '$1$3$2') - // console.log(`8. ${toFormat}`) // 9. preppend to wrapped word - // ([a-zA-Z]+ - find text to prepend + // [a-zA-Z]+ - find text to prepend // ]*> - find opening tag before word // [a-zA-Z]+ - find word itself // <\/span> - find closing tag after word toFormat = toFormat.replace(/([a-zA-Z]+)(]*>)([a-zA-Z]+)(<\/span>)/g, '$2$1$3$4') - // console.log(`9. ${toFormat}`) // 10. extract delimiters outside of spans // ]*> - find opening tag before word @@ -89,27 +78,33 @@ const underlineNonBip39words = (element, /*component*/ content) => { /(]*>)(\s|[,;])*([a-zA-Z]+)(\s|[,;])*(<\/span>)/g, '$2$1$3$5$4' ) - // console.log(`10. ${toFormat}`) // 11 remove empty spans toFormat = toFormat.replace(/]*><\/span>/g, '') - // console.log(`11. ${toFormat}`) // 12. translate non-breaking space back to html // warning: this translates spaces inside span attributes as well, - // but it doesn't matter for next step + // but it doesn't matter for the next steps toFormat = toFormat.replace(/\s/g, ' ') - // console.log(`12. ${toFormat}`) + // 13. extract raw words into array + // ]*> - find opening tag + // [^<>]* - find element content + // <\/span>) - find closing tag const words = matchAll(/]*>[^<>]*<\/span>/g, toFormat).map((wrappedWord) => - wrappedWord.replace(/(]*>)([^<>]*)(<\/span>)/g, '$2').replace(/[,;]/g, '') + wrappedWord.replace(/(]*>)([^<>]*)(<\/span>)/g, '$2').replace(/(\s|[,;])/g, '') ) + + // 14. reapply style rules to each word const areWordsBipP39 = words.map((word) => isBip39Word(word)).reverse() - const styleReplacer = (match, p1, p2, p3, offset, string) => { - const style = areWordsBipP39.pop() ? '' : ' class="not-bip-39"' - return `${p2}${p3}` - } - const formattedText = toFormat.replace(/(]*>)([^<>]*)(<\/span>)/g, styleReplacer) + const formattedText = toFormat.replace( + /(]*>)([^<>]*)(<\/span>)/g, + (match, p1, p2, p3, offset, string) => { + const style = areWordsBipP39.pop() ? '' : ' class="not-bip-39"' + return `${p2}${p3}` + } + ) + const rawText = words.join(' ') element.innerHTML = `${formattedText}` setCaretPosition(element, caretPosition)