angularjs to output plain text instead of html
Asked Answered
A

8

67

I have some text like this:

<span>My text</span>

I want to display without tags:

My text

I also don't want to apply the tags, I want to strip them. What's an easy way to do that?

Angular html:

<div>{{myText | htmlToPlaintext}}</div>
Actionable answered 25/6, 2013 at 5:0 Comment(4)
You have tagged this under AngularJS, so I assume you want to do display the text using AngularJS. If so, is this text in a model? Which html tag are you using to display the contents of the model?Diphthongize
@Diphthongize I created a filter based on the answer Abhishek gave.Actionable
I see that and his solution uses jQuery - You have tagged this under AngularJS and I have a feeling that you you can do it in AngularJS without using jQuery, if only you can give more information in your question - particularly where you wish to display the text in your view...Diphthongize
@Diphthongize I added an example of what I'm doing in angularActionable
C
210

jQuery is about 40 times SLOWER, please do not use jQuery for that simple task.

function htmlToPlaintext(text) {
  return text ? String(text).replace(/<[^>]+>/gm, '') : '';
}

usage :

var plain_text = htmlToPlaintext( your_html );

With angular.js :

angular.module('myApp.filters', []).
  filter('htmlToPlaintext', function() {
    return function(text) {
      return  text ? String(text).replace(/<[^>]+>/gm, '') : '';
    };
  }
);

use :

<div>{{myText | htmlToPlaintext}}</div>  
Congruent answered 26/6, 2013 at 8:47 Comment(13)
I actually prefer String(text).replace(/<[^>]+>/gm, ''). I've been using it for years without any issues.Helpmeet
jQuery is 40 times slower, but you still get 8000 ops/s, so not using jQuery for that reason is premature optimization.Mim
@Mim you are right, 8k ops/s is enough. But think of the whole picture. Is your app doing only that ? What about mobiles ? What about heavy applications ? Is there any browser compatibility issue involved ? What are the advantages of jQuery ? Is jQuery more readable ? Is jQuery easy to write ? Sometimes jQuery is good enough. But jQuery should not be used everywhere. Especially not here.Congruent
I would never add a jQuery dependency just to convert html to text, but if my project already used jQuery I would choose the jQuery solution because I consider a custom-written regular expression less readable, less tested and less reliable. Does your regular expression protect against all possible forms of XSS?Mim
@Blaise, if you add the text into the DOM with jQuery, you don't have to protect against XSS into this function. jQuery does it when added to the DOM. BTW, I'm really not sure which one is more readable.Congruent
using the DOM engine covers a lot more cases that this simple replace those not example: some codes here &#146; &#147; &#148;Chaparajos
You should probably add a null-check in there, or it will output "null": return text ? String(text).replace(/<[^>]+>/gm, '') : "";Josefajosefina
I'm wary of this solution. There's a number of circumstances where it will fail: 1. A less than sign '<' appearing in the text that's not a tag, i.e. <p>One < Two</p>. The string "< Two</p" will be deleted erroneously. 2. It won't convert character references like &amp; or more pertinently &lt;Omega
You could shorten the regexp with a nongreedy search /<.+?>/gm, which looks a bit more intuitive, readable and also saves you a few characters.Valida
This does not work if the html text is following. "<p><span style="color: rgb(34, 36, 38);text-align: left;float: none;background-color: rgb(255, 255, 255);">Some Text.</span><!--EndFragment--><br/><br/><br/></p>"Malevolent
@SamarthAgarwal what's wrong? it returns Some Text., as I would expect itCongruent
How to show the preview ,instead of showing the plain text(it is working). but i need to show the preview like stack overflow shows while posting question or answer including images alsoGrubby
This will not work if there are close angle brackets in attributes or comments. For example, <img src="file>.jpg" width="640" height="400" alt="image"><p><a href="http://example.com/path?var=>&utm_campaign=123">Hello</a><!-- sun > world -->World</p>Jun
P
21

from https://docs.angularjs.org/api/ng/function/angular.element

angular.element

wraps a raw DOM element or HTML string as a jQuery element (If jQuery is not available, angular.element delegates to Angular's built-in subset of jQuery, called "jQuery lite" or "jqLite.")

So you simply could do:

angular.module('myApp.filters', []).
  filter('htmlToPlaintext', function() {
    return function(text) {
      return angular.element(text).text();
    }
  }
);

Usage:

<div>{{myText | htmlToPlaintext}}</div>
Peterec answered 4/6, 2014 at 19:41 Comment(8)
I would avoid this approach as well; might not take as long as full jQuery, but certainly much slower than accepted answer.Lizalizabeth
I suggest wrapping your text in an element otherwise a plain old string like "hi" will return an empty string angular.element('<div>'+text+'</div>').text();Incoming
if you're in the link function of a directive you can simply do element.text() 0.oCrouch
I prefer this solution to using a regex, at least in cases where speed isn't critical. It's more correct and will actually convert the html to plain text, extraneously less than signs, special entities and all.Omega
How to show the preview ,instead of showing the plain text(it is working). but i need to show the preview like stack overflow shows while posting question or answer including images alsoGrubby
If your html have inline style then accepted answer fails, this way works fine :)Yawl
Kudos to this, using regex is quick but there will be edge cases where it fails. This is a simpler and safer way when performance is not critical. Thanks!Ferullo
This will fail if text is not already wrapped in some HTML tag. So to be robust it should be more like: return angular.element('<div>' + text + '</div>')Talanian
F
4
var app = angular.module('myapp', []);

app.filter('htmlToPlaintext', function()
{
    return function(text)
    {
        return  text ? String(text).replace(/<[^>]+>/gm, '') : '';
    };
});

<p>{{DetailblogList.description | htmlToPlaintext}}</p>
Fizgig answered 9/3, 2016 at 7:8 Comment(4)
add some formating an some insights to the code, that helps to generate better answers.Landes
Please add some explanation. Your answer is currently flagged "low quality" and might eventually be removed.Erastian
There's a difference between a low-quality answer that should be voted down and a non-answer that should be deleted. Please see You're doing it wrong: A plea for sanity in the Low Quality Posts queue.Horntail
How to show the preview ,instead of showing the plain text(it is working). but i need to show the preview like stack overflow shows while posting question or answer including images alsoGrubby
G
3

You want to use the built-in browser HTML strip for that instead of applying yourself a regexp. It is more secure since the ever green browser does the work for you.

angular.module('myApp.filters', []).
  filter('htmlToPlaintext', function() {
    return function(text) {
      return stripHtml(text);
    };
  }
);

var stripHtml = (function () {
  var tmpEl = $document[0].createElement("DIV");
  function strip(html) {
    if (!html) {
      return "";
    }
    tmpEl.innerHTML = html;
    return tmpEl.textContent || tmpEl.innerText || "";
  }
  return strip;
}());

The reason for wrapping it in an self-executing function is for reusing the element creation.

Gaynor answered 8/12, 2015 at 14:5 Comment(2)
How to show the preview ,instead of showing the plain text(it is working). but i need to show the preview like stack overflow shows while posting question or answer including images alsoGrubby
changed $document[0] to document and it worked for me! Thank youGallardo
C
3

<div ng-bind-html="myText"></div> No need to put into html {{}} interpolation tags like you did {{myText}}.

and don't forget to use ngSanitize in module like e.g. var app = angular.module("myApp", ['ngSanitize']);

and add its cdn dependency in index.html page https://cdnjs.com/libraries/angular-sanitize

Cotonou answered 26/7, 2017 at 5:44 Comment(0)
A
0

You can use ng-bind-html, don't forget to inject $sanitize service into your module Hope it helps

Abagael answered 13/4, 2017 at 0:35 Comment(0)
T
-3

Use ng-bind-html this is only proper and simplest way

Teary answered 3/1, 2017 at 10:30 Comment(1)
Welcome to Stack Overflow. Please add more details for clarification. Once you have sufficient reputation you will be able to comment on any post; instead, provide answers that don't require clarification from the OP.Brandnew
S
-7

Use this function like

 String.prototype.text=function(){
   return this ? String(this).replace(/<[^>]+>/gm, '') : '';
 }

  "<span>My text</span>".text()
  output:
  My text

Fiddle

Smollett answered 25/6, 2013 at 5:9 Comment(4)
This is a jQuery-based solution. The question was about angularjs.Farmann
Rev The mark answer is javascript and if I did it using jquery what make it differenceSmollett
Your solution is not compatible with OP's requirements. he already built his app on angularjs. jquery is a different framework.Rocha
+1 and I don't see here any jQuery... wtf? Another problem is @Abjo's method extends build in String prototype. That some developers choose to be angry about.Salesgirl

© 2022 - 2024 — McMap. All rights reserved.