Lesson 3 - Angular - 1920
Lesson 3 - Angular - 1920
3rd
Activity - Intro to Angular
2019/2020
Outputting posts 2
Structural directives 3
*ngFor directive 3
*ngIf directive 3
Creating Posts with Property and Event Binding 4
@Output decorator 5
Linking data between components 5
@Input decorator 6
4. Exercise 6
1. Outputting posts
The goal is to be able to output the posts, so perform the following steps:
a) Create a new component inside posts folder and name it post-list and in there,
add post-list.component.ts and the post-list.component.html
ng g c posts/post-list --spec=false
c) Add post-list selector in the app.component.html page to have the post list
appear just after the post create
f) Use the expansion panel which is a collapsible, from angular material and import
all the files needed (MatExpansionModule) in order to have something like this:
1
f) Add the module needed in app.module.ts
app.module.ts
g) Do a stylish step
post-create.component.css
mat-form-field,textarea{
width: 100%;
}
app.component.html app.component.css
<app-header></app-header> main {
<main> width: 80%;
margin: 1rem auto;
<app-post-create></app-post-create> }
<app-post-list></app-post-list>
</main>
2
2. Structural directives
a)*ngFor directive
We want to create an array of objects to simulate posts content and add a way to go
through all the elements of the array. We do this adding the content in the ts file, and
angular has an instruction that change the HTML DOM, that allow us to repeat an element
as often as required - *ngFor . Here we have a new array of posts with 3 objects.
post-list.component.ts
post-list.component.html
<mat-accordion multi="true">
<mat-expansion-panel *ngFor="let post of posts">
<mat-expansion-panel-header>
{{post.title}}
</mat-expansion-panel-header>
<p>{{post.content}}</p>
</mat-expansion-panel>
</mat-accordion>
3
The:
is a javascript way to go through arrays. We are creating a variable post that we can access
later in the HTML. In each iteration, a post will be an object that has two properties: title
and content. We can access to these values through string interpolation
{{post.title}}
a)*ngIf directive
And if the posts array is empty, how can we handle that case?
Well, Angular has another directive that allows us to test conditions the - *ngIf. In this
case we test if we have any post, and we only show that data if the condition is true. So, if
we don’t we make an alternative HTML. In this case, our alternate HTML is
post-list.component.ts post-list.component.html
4
import { Component, Input } from '@angular/core'; <mat-accordion multi="true" *ngIf="posts.length > 0">
<mat-expansion-panel *ngFor="let post of posts">
@Component({ <mat-expansion-panel-header>
selector: 'app-post-list', {{post.title}}
templateUrl: './post-list.component.html', </mat-expansion-panel-header>
styleUrls: [ '/post-list.component.css' ] <p>{{post.content}}</p>
}) </mat-expansion-panel>
export class PostListComponent { </mat-accordion>
<p *ngIf="posts.length <= 0”>There are no posts, yet!</p>
posts = [];
}
Now we want to send our post created to the post-list, in order to see all the posts listed.
For this we have to code the following activities:
a) save the user input and create a method to send it to another component.
b) gather the user input, save it in an array with all the posts and create a method to
send it to other component
5
c) receive the data from an external component. For this, we’ll make some changes, to
create a post title and post content. We create another input field for the posts Title and
delete the {{newPost}} and the <p> element. We also made some styling changes, just
following the rules.
6
@Output decorator
Save the user input and create a method to send it to another component.
post-create.component.ts post-create.component.html
The method onAddPost() will create an object with the user input data, and will send it
via a special kind of variable, an event Emitter with a special attribute @Output(), which
is called decorator.
This decorator allows a data emitter to send its data to his father (the component that
calls it) - app.component.ts
7
Linking data between components
Gather the user input, save it in an array with all the posts and create a method to
send it to another component. The component that will receive the data sent is the
father component. So in app.component will receive the post created and will
stored the data in an array. The way we do this is by running
(postCreated)="onPostAdded($event)"
where postCreated is the event from the post-create component that is sending
data, to our new function onPostAdded in app.component. The way we receive our
data is accessing the object of the event, which is $event.
We then save the post in an array that will be available from other components. In
this case, post-list, but first let’s put it ready for receiving data from other
components. Go to the @Input decorator section..
8
@Input decorator
In our template we need the post.title and post.content of all posts. For that we need to
receive the posts array and that’s why we create an array named posts. But it's a special
array that we’ll be fed by external data, and to inform angular of this feature we use
@Input().
Having this array loaded, we now have all the data we need to traverse the array and list
all the posts with our *ngFor.
9
3. Exercise
Create another input field named authorName, and show it in the list of posts.
10