当 HTML 可能有子元素时,如何 Javascript 用新文本替换 HTML 文本
How to Javascript to replace HTML text with new text when the HTML may have children elements
我正在尝试使用 JavaScript 搜索所有 p 元素以查找正则表达式,但我要查找的文本可能部分存在于属性元素中或包含在其中,也可能不存在一个跨度。最终,我计划修复 HTML 代码中应用于 Word 项目符号项的交叉引用,方法是添加一个属性元素,该元素引用我之前插入的 html id JavaScript.
我的总体项目是创建一个 Word 文档,我使用“另存为”功能让 Word 创建一个过滤后的 HTML 文件。我最终使用 JavaScript 来插入 ID 和标签,这样我就可以利用 CSS 文件来标准化我所有 HTML 文件的格式。因此,我对初始 HTML 代码的控制有限。
到目前为止,我已经能够创建遍历所有 p 元素的循环。在循环中,我能够为“/Step (\d+)/”的 innerText 上的正则表达式执行条件语句,因为我希望文本看起来类似于第 1 步、第 12 步或任何其他数字。下面的代码似乎成功进入了 if 语句。我 运行 遇到了 innerHTML 部分的替换函数的麻烦,因为 innerText 匹配表达式,但 innerHTML 包含阻止我正在寻找的最终结果的元素.我希望能够一般地解释任何其他元素,例如粗体、斜体、a 等。为此,我尝试使用多个 if 语句来替换各种潜在的 HTML 条件。
我试图通过将粗体应用于文本来弄清楚这项技能,以确保我了解如何完成此特定功能。到目前为止,我所做的所有搜索都有助于使正则表达式匹配 innerText,但我找不到方法或忽略无关的 html 代码。我当时在想,可以用新的 HTML 代码存储替换的 innerText,然后将其设为新的 innerHTML,但我想维护的 p 元素中可能有其他格式。
我采用的方法是为内部 HTML 替换使用第二个正则表达式,贪婪搜索似乎我会捕获错误结果,即使正则表达式正在捕获它。
HTML
<p id="FirstPara" class=firstpara>This is a header</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎ </span><b>1</b>.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>2.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>1 and Step <span lang=HE>‎</span>2.</p>
JavaScript函数
function findTheText() {
regExp1 = /Step (\d)/g;
for (var i = 0; i < document.getElementsByTagName('p').length; i++) {
alert(i+" - "+j+" - "+document.getElementsByTagName('p')[i].innerHTML+" - "+results[j]);
var results = document.getElementsByTagName('p')[i].innerText.match(regExp1);
if (results !== null) {
for (var j = 0; j < results.length; j++) {
var replace = results[j].replace(/Step\s/,"");
var regExp2 = new RegExp('Step\s'+replace,"i");
var regExp3 = new RegExp('Step\s.*>'+replace,"i");
var regExp4 = new RegExp('Step\s.*>.*>'+replace,"i");
var results2 = document.getElementsByTagName('p')[i].innerText.match(regExp2);
var results3 = document.getElementsByTagName('p')[i].innerText.match(regExp3);
var results4 = document.getElementsByTagName('p')[i].innerText.match(regExp4);
if (results2 !== null) {
document.getElementsByTagName('p')[i].innerHTML.replace(regExp2, "<b>"+results[j]+"</b>");
} else if (results3 !== null) {
document.getElementsByTagName('p')[i].innerHTML.replace(regExp3, "<b>"+results[j]+"</b>");
} else if (results4 !== null) {
document.getElementsByTagName('p')[i].innerHTML.replace(regExp4, "<b>"+results[j]+"</b>");
}
}
}
}
}
截至目前,代码将找到我想要的文本,但由于正则表达式匹配我正在寻找的字符串,但内部 HTML 不匹配我没有实现粗体(或最终属性)在文本上。
预期HTML输出
<p class=firstpara>This is a reference to <b>Step 1</b>.</p>
<p class=firstpara>This is a reference to <b>Step 2</b>.</p>
<p class=firstpara>This is a reference to <b>Step 1</b> and <b>Step 2</b>.</p>
我不太确定这是您期望的结果,但这段代码可能有效。您甚至可以更新它以使用箭头函数和模板文字。
function findTheText() {
let regExp1 = /Step (\d)/g;
let paragraphs = document.getElementsByTagName('p');
for (var i = 0; i < paragraphs.length; i++) {
let spans = Array.from(paragraphs[i].getElementsByTagName('span'));
spans.forEach(function(child) {
paragraphs[i].removeChild(child);
})
if (paragraphs[i].innerHTML.match(regExp1)) {
let replace = paragraphs[i].innerHTML.match(regExp1);
replace.forEach(function(match) {
paragraphs[i].innerHTML = paragraphs[i].innerHTML.replace(match, "<b>" + match + "</b>");
})
};
}
}
findTheText()
<p id="FirstPara" class=firstpara>This is a header</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎ </span>1.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>2.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>1 and Step <span lang=HE>‎</span>2.</p>
您可以删除所有子 span
s,然后检查 textContent
以忽略其余标记(如 <b>
s),捕获步骤数字并替换为被 <b>
和 </b>
:
包围
document.querySelectorAll('p').forEach((p) => {
p.querySelectorAll('span').forEach(span => span.remove());
p.innerHTML = p.textContent.replace(/Step +(\d+)/g, '<b>Step </b>');
});
<p id="FirstPara" class=firstpara>This is a header</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎ </span><b>1</b>.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>2.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>1 and Step <span lang=HE>‎</span>2.</p>
仅删除 lang
为 HE
的 span
:
document.querySelectorAll('p').forEach((p) => {
p.querySelectorAll('span[lang="HE"]').forEach(span => span.remove());
p.innerHTML = p.textContent.replace(/Step +(\d+)/g, '<b>Step </b>');
});
<p class=firstpara>This is a <span>reference</span> to Step <span lang=HE>‎ </span><b>1</b>.</p>
我正在尝试使用 JavaScript 搜索所有 p 元素以查找正则表达式,但我要查找的文本可能部分存在于属性元素中或包含在其中,也可能不存在一个跨度。最终,我计划修复 HTML 代码中应用于 Word 项目符号项的交叉引用,方法是添加一个属性元素,该元素引用我之前插入的 html id JavaScript.
我的总体项目是创建一个 Word 文档,我使用“另存为”功能让 Word 创建一个过滤后的 HTML 文件。我最终使用 JavaScript 来插入 ID 和标签,这样我就可以利用 CSS 文件来标准化我所有 HTML 文件的格式。因此,我对初始 HTML 代码的控制有限。
到目前为止,我已经能够创建遍历所有 p 元素的循环。在循环中,我能够为“/Step (\d+)/”的 innerText 上的正则表达式执行条件语句,因为我希望文本看起来类似于第 1 步、第 12 步或任何其他数字。下面的代码似乎成功进入了 if 语句。我 运行 遇到了 innerHTML 部分的替换函数的麻烦,因为 innerText 匹配表达式,但 innerHTML 包含阻止我正在寻找的最终结果的元素.我希望能够一般地解释任何其他元素,例如粗体、斜体、a 等。为此,我尝试使用多个 if 语句来替换各种潜在的 HTML 条件。
我试图通过将粗体应用于文本来弄清楚这项技能,以确保我了解如何完成此特定功能。到目前为止,我所做的所有搜索都有助于使正则表达式匹配 innerText,但我找不到方法或忽略无关的 html 代码。我当时在想,可以用新的 HTML 代码存储替换的 innerText,然后将其设为新的 innerHTML,但我想维护的 p 元素中可能有其他格式。
我采用的方法是为内部 HTML 替换使用第二个正则表达式,贪婪搜索似乎我会捕获错误结果,即使正则表达式正在捕获它。
HTML
<p id="FirstPara" class=firstpara>This is a header</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎ </span><b>1</b>.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>2.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>1 and Step <span lang=HE>‎</span>2.</p>
JavaScript函数
function findTheText() {
regExp1 = /Step (\d)/g;
for (var i = 0; i < document.getElementsByTagName('p').length; i++) {
alert(i+" - "+j+" - "+document.getElementsByTagName('p')[i].innerHTML+" - "+results[j]);
var results = document.getElementsByTagName('p')[i].innerText.match(regExp1);
if (results !== null) {
for (var j = 0; j < results.length; j++) {
var replace = results[j].replace(/Step\s/,"");
var regExp2 = new RegExp('Step\s'+replace,"i");
var regExp3 = new RegExp('Step\s.*>'+replace,"i");
var regExp4 = new RegExp('Step\s.*>.*>'+replace,"i");
var results2 = document.getElementsByTagName('p')[i].innerText.match(regExp2);
var results3 = document.getElementsByTagName('p')[i].innerText.match(regExp3);
var results4 = document.getElementsByTagName('p')[i].innerText.match(regExp4);
if (results2 !== null) {
document.getElementsByTagName('p')[i].innerHTML.replace(regExp2, "<b>"+results[j]+"</b>");
} else if (results3 !== null) {
document.getElementsByTagName('p')[i].innerHTML.replace(regExp3, "<b>"+results[j]+"</b>");
} else if (results4 !== null) {
document.getElementsByTagName('p')[i].innerHTML.replace(regExp4, "<b>"+results[j]+"</b>");
}
}
}
}
}
截至目前,代码将找到我想要的文本,但由于正则表达式匹配我正在寻找的字符串,但内部 HTML 不匹配我没有实现粗体(或最终属性)在文本上。
预期HTML输出
<p class=firstpara>This is a reference to <b>Step 1</b>.</p>
<p class=firstpara>This is a reference to <b>Step 2</b>.</p>
<p class=firstpara>This is a reference to <b>Step 1</b> and <b>Step 2</b>.</p>
我不太确定这是您期望的结果,但这段代码可能有效。您甚至可以更新它以使用箭头函数和模板文字。
function findTheText() {
let regExp1 = /Step (\d)/g;
let paragraphs = document.getElementsByTagName('p');
for (var i = 0; i < paragraphs.length; i++) {
let spans = Array.from(paragraphs[i].getElementsByTagName('span'));
spans.forEach(function(child) {
paragraphs[i].removeChild(child);
})
if (paragraphs[i].innerHTML.match(regExp1)) {
let replace = paragraphs[i].innerHTML.match(regExp1);
replace.forEach(function(match) {
paragraphs[i].innerHTML = paragraphs[i].innerHTML.replace(match, "<b>" + match + "</b>");
})
};
}
}
findTheText()
<p id="FirstPara" class=firstpara>This is a header</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎ </span>1.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>2.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>1 and Step <span lang=HE>‎</span>2.</p>
您可以删除所有子 span
s,然后检查 textContent
以忽略其余标记(如 <b>
s),捕获步骤数字并替换为被 <b>
和 </b>
:
document.querySelectorAll('p').forEach((p) => {
p.querySelectorAll('span').forEach(span => span.remove());
p.innerHTML = p.textContent.replace(/Step +(\d+)/g, '<b>Step </b>');
});
<p id="FirstPara" class=firstpara>This is a header</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎ </span><b>1</b>.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>2.</p>
<p class=firstpara>This is a reference to Step <span lang=HE>‎</span>1 and Step <span lang=HE>‎</span>2.</p>
仅删除 lang
为 HE
的 span
:
document.querySelectorAll('p').forEach((p) => {
p.querySelectorAll('span[lang="HE"]').forEach(span => span.remove());
p.innerHTML = p.textContent.replace(/Step +(\d+)/g, '<b>Step </b>');
});
<p class=firstpara>This is a <span>reference</span> to Step <span lang=HE>‎ </span><b>1</b>.</p>