63

I wish the have a ul element and then in my json I have html containing list (li) elements from various social media sites.. when I put ngfor on the list items is creates multiple ul's for each of the outputted json records.. is it possible just to output each of the li's as plain html and not wrap them in an element

small sample of my json

{
    "courses": [{
        "tile_id": 0,
        "tile_content": "<li class=\"grid-item horiz-double blog-tile\" data-item-id=\"0\">yrdy<\/li>"
    }],
}

small sample of my angular service - this works perfectly and outputs the json but maybe im missing some kind of formatting setting

public getCourses() {

    this._http.get(this.apiUrl).map(response => response.json()).subscribe(data => {
        // console.log( data.courses );
        this._dataStore.courses = data.courses;

        // console.log(this._coursesObserverXX);

        this._coursesObserverXX.next(this._dataStore.courses);

    }, error => console.log('Could not load courses.'));

}

and my html

<ul class="list-group" *ngFor="#course of courses | async">
      {{ course.tile_content }}
</ul>

the goal is to not have the ngfor output a wrapper and also to display the output as plain html rather than plaintext as it appears to come out

Jacob Stamm
  • 1,660
  • 1
  • 29
  • 53
Kravitz
  • 2,769
  • 6
  • 26
  • 53

3 Answers3

203

In some cases, <ng-container> may be useful. Like (not for this specific question):

<ng-container *ngFor="let item of items; let i = index">
  ...
</ng-container>

In the DOM, its content is rendered as usual, but the tag itself is rendered as an HTML comment.

From the documentation:

Group sibling elements with <ng-container>

[...]

<ng-container> to the rescue

The Angular <ng-container> is a grouping element that doesn't interfere with styles or layout because Angular doesn't put it in the DOM.

Community
  • 1
  • 1
Arjan
  • 22,808
  • 11
  • 61
  • 71
  • 1
    gosh, why didn't I think of this. Been racking brain for hours trying to figure something out. Changed my div to a ng-container and now I can use simple css to achieve what I was trying to do – Ronnie Feb 27 '20 at 00:31
  • For those who came from react, think of `ng-container` as angular equivalent to `React.Fragment` in React – Ahmed Shaqanbi Dec 31 '21 at 09:34
6

Not sure to understand what you want / try to do but you can do something like this:

<ul class="list-group">
  <li *ngFor="#course of courses | async">
    {{ course.tile_content }}
  </li>
</ul>

Note that the expanded syntax could also be used:

<template ngFor [ngForOf]="courses | async" #course>
  {{ course.tile_content }}
</template>

(the template tag won't be added into the HTML)

Edit

This works:

<ul *ngFor="#elt of elements | async" [innerHTML]="elt.title">
</ul>

See this plunkr: https://plnkr.co/edit/VJWV9Kfh15O4KO8NLNP3?p=preview

Liam
  • 27,717
  • 28
  • 128
  • 190
Thierry Templier
  • 198,364
  • 44
  • 396
  • 360
  • The second option is probably more what im looking for... im looking to just dump the json in between the ul tags.. will doing it that way output raw html and do I use the second method by making a directive... sorry pretty new to angular so I may be using the wrong term – Kravitz May 03 '16 at 13:16
  • No worries. Using the `innerHTML` attribute is possible at the level of the ngFor ;-) I updated my answer... – Thierry Templier May 03 '16 at 13:19
  • I added a plunkr demonstrating this – Thierry Templier May 03 '16 at 13:20
  • Thanks dude, so I made a new directive and this is working for me @Component({ selector: 'social-wall', template: ``, }) but its not plain html any idea how i work that in at this level – Kravitz May 03 '16 at 13:56
  • I think that the `innerHTML` attribute is what you should use. It will allow you to render the HTML... – Thierry Templier May 03 '16 at 14:04
  • When I add that to the long template syntax it doesnt work in fact it breaks it, do you have an example of how it might work with it – Kravitz May 03 '16 at 14:08
5

You can use outerHTML

<ul class="list-group" >
  <li *ngFor="let course of courses | async" [outerHtml]="course.tile_content"></li>
</ul>

Plunker example

Liam
  • 27,717
  • 28
  • 128
  • 190
Günter Zöchbauer
  • 623,577
  • 216
  • 2,003
  • 1,567
  • Not quite what im after.. you see the li tag will be supplied by the json result - I essentially need to dump the json between the ul tags as raw html – Kravitz May 03 '16 at 13:17
  • Sorry, forgot to move the `*ngFor` to the `
  • ` element. Now it produces the expected HTML.
  • – Günter Zöchbauer May 03 '16 at 13:19
  • Did you check the Plunker? It's now generating `
  • ` that are not wrapped with `
      `
  • – Günter Zöchbauer May 03 '16 at 13:45
  • Cheers man, I ended up using this as a base point and scrapped the idea of creating a new directive. – Kravitz May 03 '16 at 14:48
  • I've used `[outerHtml]` and found that when the contents (observable) changed it couldn't update it because the node was of course now gone! My guess is that would happen here too. If it does you can wrap each `li` like this: `
  • ` – Simon_Weaver Jul 28 '21 at 01:32