I want to convert <font> element to <span> element like this using regex:
Input:
[some strings...]<span [something]></span><font ...>[sometext]</font>[some strings...]
Output:
[some strings...]<span [something]>[sometext]</span>[some strings...]
Note: The input/output is a string.
In shortly, I want to remove the <font> element and move the contents of that into <span> element keeping the attributes of the <span> element.
I've tried this:
const rx = /<span(.*?)><\/span>([^<\\s]+?|\\s*)<font(?:\\s+[^>]*)?>(.*?)<\/font>/gi;
inputStr.replace(rx, function(match, p1, p2, p3) { return `${p2}<span${p1}>${p3}</span>`; });
However it doesn't work.
Can anyone help me?
I also agree with #skyboyer, this is not the best way, but if you can use regexp only or if this is a one-time task, you can use a class group specifing to take all chars that are not ">", in this way you can take all the params of the tag span and use it in the font:
var text = 'Some text... <span style="color:red"></span><font style="margin:10px">Hi there!</font> other text <span style="color:blu"></span><font style="margin:10px">doh!</font> final text';
console.log(text.replace(/<span([^>]*)><\/span><font[^>]*>(.+?)<\/font>/gi,'<span$1>$2</span>'));
edited in order to match other tags inside (except other s, obviously)
Use any ID or class selector if possible, I have used here tag name just for example, if you have a Id selector then remove [0] from code.
This or with some modification should work for you
document.getElementsByTagName("font")[0].replaceWith('<span>' + document.getElementsByTagName("font")[0].innerHTML +'</span>')
Using Jquery,
$("YOUR_DOM_SELECTOR").replaceWith('<span>' + $("YOUR_DOM_SELECTOR").html() +'</span>')
Related
I recently started learning/using about RegEx.
Is there a way to avoid matching words that are HTML tag attributes or belonging to tag attributes?
For example:
<p style=“position: absolute”>position: </p>
I tried
/\bposition\b\W\s/g
But that matches both instances.
Can I only match the second “position: “?
Clarification:
I am trying to search the document for words that the user enters and replace them with a span element containing those words - this is similar to "Ctrl + F". Simply having the text is not enough as I would need a way to also update the document once the text was replaced with the span elements.
Disclaimer: Use stuff like document.innerText and other DOM APIs rather than Regex.
Match HTML tags:
<.+?>/g
Match everything within HTML tags (should handle nested ones as well):
/(?<=<.+.>)(.*?)(?=<.*\/.+.?>)/g
https://regex101.com/r/2uZHli/ for example of the above.
The RegEx to match the HTML / XML tags is /(<([^>]+)>)/ig. Maybe be this is what you're looking for.
let str = '<p style="position: absolute">position: </p>';
const strWithoutTag = str.replace(/(<([^>]+)>)/ig, '');
console.log(strWithoutTag);
You can try the Regex to match your temp, which matched the second "position: ".
/(?=\b.*(?<yourKeyword>position).*\b)(?<=<[^]*>)([^<>]+)(?=<\/([^<>]*)>)/g
I want to render a text as common HTML and parse occurrences of [code] tags that should be output unrendered - with the tags left untouched.
So input like this gets processed accordingly:
<p>render as HTML here</p>
[code]<p>keep tags visible here</p>[/code]
<p>more unescaped text</p>
I've regexed all code-tags but I have no idea how to properly set the text of the element afterwards. If I use jQuery's text() method nothing gets escaped, if I set it with the html() method everything gets rendered and I gained nothing. Can anybody give me a hint here?
Try replacing [code] with <xmp> and [/code] with </xmp> using regex or alike, and then use the jQuery html() function.
Note that <xmp> is technically deprecated in HTML5, but it still seems to work in most browsers. For more information see How to display raw html code in PRE or something like it but without escaping it.
You could replace the [code] and [/code] tags by <pre> and </pre> tags respectively, and then replace the < within the <pre> tags by & lt;
A programmatic solution based on Javascript is as follows
function myfunction(){
//the string 's' probably would be passed as a parameter
var s = "<p>render as HTML here</p>\
[code]<p>keep tags visible here</p>[/code]\
<p>more unescaped text</p>";
//keep everything before [code] as it is
var pre = s.substring(0, s.indexOf('[code]'));
//replace < within code-tags by <
pre += s.substring(s.indexOf('[code]'), s.indexOf('[/code]'))
.replace(new RegExp('<', 'g'),'<');
//concatenate the remaining text
pre += s.substring(s.indexOf('[/code]'), s.length);
pre = pre.replace('[code]', '<pre>');
pre = pre.replace('[/code]', '</pre>');
//pre can be set as some element's innerHTML
return pre;
}
I would NOT recommend the accepted answer by Andreas at all, because the <xmp> tag has been deprecated and browser support is totally unreliable.
It's much better to replace the [code] and [/code] tags by <pre> and </pre> tags respectively, as raghav710 suggested.
He's also right about replacing the < character with <, but that's actually not the only character you should replace. In fact, you should replace character that's a special character in HTML with corresponding HTML entities.
Here's how you replace a character with its corresponding HTML entity :
var chr = ['&#', chr.charCodeAt(), ';'].join('');
You can replace the [code]...[/code] with a placeholder element. And then $.parseHTML() the string with the placeholders. Then you can insert the code into the placeholder using .text(). The entire thing can then be inserted to the document (run below or in JSFiddle).
var str = "<div><b>parsed</b>[code]<b>not parsed</b>[/code]</div>";
var placeholder = "<div id='code-placeholder-1' style='background-color: gray'></div>";
var codepat = /\[code\](.*)\[\/code\]/;
var code = codepat.exec(str)[1];
var s = str.replace(codepat, placeholder);
s = $.parseHTML(s);
$(s).find("#code-placeholder-1").text(code);
$("#blah").html(s);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
Text
<div id="blah">place holder</div>
Around
The code above will need some modifications if you have multiple [code] blocks, you will need to generate a unique placeholder id for each code block.
If you may be inserting untrusted structure code, would highly recommend using large random number for the placeholder id to prevent a malicious user from hijacking the placeholder id.
I want to replace the "word" that is outside "span", and keep the other that is inside "span". By now, the following code works when both are following "mark>" and followed by "span". But I want to go further, following "mark>" OR being followed by "span", any one of the two condition should cause replacing action.
var replaceString = "newWord";
var htmlString = "This <span style='color:red' title='mark'>normal word</span> need no change. This word is to be replaced. <span>Another word</span> need no change.";
var reg=new RegExp("(?!mark>)"+replaceString+"(?!<\/span>)","gi");
var bb=htmlString.replace(reg,replaceString);
alert(bb)
// Final result should be "This <span style='color:red' title='mark'>normal word</span> need no change. This newWord is to be replaced. <span>Another word</span> need no change.";
UPDATE: using title as mark. adding starting tag span
UPDATE: Follow the suggestion below, I'm trying to solve the problem in anohter way, see here: js regex: replace words not in a span tag
Would you be comfortable using another span tag ?
By putting a class name inside it, you should be able to change the words you need to change by changing the content of every span containing that class.
Something like :
This <span style='color:red' mark>word</span> need no change. This <span class='changeMe'>word</span> is to be replaced. Another word</span> need no change.
And a jQuery script going
$('.changeMe').text("newWord")
If you still want to use Regexp, for an OR condition, you might just do it twice :
var reg=new RegExp("(?!mark>)"+replaceString,"gi");
var bb=htmlString.replace(reg,replaceString);
reg=new RegExp(replaceString+"(?!<\/span>)","gi");
bb=htmlString.replace(reg,replaceString);
You are looking for negative look-aheads (or Lookbehinds) which JS, unfortunately, doesn't support. Check http://www.regular-expressions.info/javascript.html
You may try the following Regex:
var reg = new RegExp('[^(mark>)]word[^(</span>)]', "gi")
htmlString.replace(reg, " newWord "); //Check the spaces
I would rather suggest using JS to get DOM elements and replace text iterative-lly (not sure if it's a word, even a jargon).
HTH
I'm aware you can do something like this:
$('.document-content p:has(br)').next('p').addClass("newClass")
to check whether a p tag has a br tag inside:
<p>
<br>
</p>
How to check if there's also for the existence of ANY string inside?
<p>
"Some text"
<br>
</p>
(The reason is, I want to remove all br inside the p tags that have a string inside.)
You can use the :contains selector:
$('.document-content contains("some text")').next('p').addClass("newClass")
If the string to find is stored in a variable you would need to concatenate it in the selector:
var searchString = 'some text';
$('.document-content contains("' + searchString + '")').next('p').addClass("newClass")
The reason is, I want to remove all br inside the p tags that have a string inside.
In this case you can get the text() of the element and overwrite the html() with it:
$('.document-content').html(function() {
return $(this).text();
});
Or
$('.document-content').html($('.document-content').text());
Both the above will work, the latter is shorter but (IMO) uglier and makes another DOM request.
Example fiddle
You can do something like thi https://jsfiddle.net/joL9xh2r/
$('p').each(function(i,ele){
if($(ele).text().replace(/\s/g, '').length>0)
{
alert($(ele).attr('id')+' has string');
}
})
Here are two paragraphs , one with string inside, and one without text, you can check if the paragraph contains a string using text(), Now you can do whatever you want within the if condition, its only true whan there is a string inside the p element
Now if you want to removethe br tag , then you can do this,
https://jsfiddle.net/joL9xh2r/1/
$(ele).html($(ele).text())
But, Remember this will remove all the html tags inside, for Example https://jsfiddle.net/joL9xh2r/2/,
here you have
<p id='x'>
"Some text"
<br/>
<b>abc</b>
</p>
A bold tag within p , so the above solution, and the one suggested by rorry will remove the b tag as well.
The best way to remove only br this would be
https://jsfiddle.net/joL9xh2r/3/
$('p').each(function(i,ele){
if($(ele).text().replace(/\s/g, '').length>0)
{
alert($(ele).attr('id')+' has string');
$(ele).find('br').remove();
}
})
I am trying to change color of a part of strings. I have a list of DOM elements, and for each of them, the text can contain some hashtags. I would like to put in color all hashtags words which could be found in the text.
Here is the begin of the code :
var listOfText = document.getElementsByClassName("titleTweet");
for (var nodetext in listOfText) {
var divContent = listOfText[nodetext].innerHTML;
if (divContent.indexOf("#") !== -1) {
// Do job here
}
}
For example, divContent can be equals to "Hello my #friends ! How are you ?"
I would like to update the dom elements to put in red color the word "#friends".
I don't know how to do that using javascript or jQuery.
You can use a regexp to find the hastags and wrap them with html. Then use the .html() method to replace the original element's html with the new string.
Example snippet
$('#myDiv').replace(/#[a-z0-1A-Z]+/g, '<span style="color: red;">$&</span>'));
Working example - http://jsfiddle.net/4p4mA/1/
Edited the example to work on all divs on the page.
Note: This will only work so long as your element only contains text, because it is replacing all the child nodes with its text value.
use regex for this, find text having hashtag and replave that in span tag for each element.
$('.titleTweet').each(function(){
var $this=$(this);
$this.html($this.text()
.replace(/#[a-z0-1A-Z]+/g, '<span style="color: red;">$&</span>'));
});
See demo here
.innerHTML is a poor basis to starting replacing text. You'll want to navigate down to the text nodes and use .nodeValue to get the text. Then you can start splitting up the text nodes.