Angular Fundamentals: Creating and Communicating between Angular Components

Kevin O'Shaughnessy
6 min readAug 3, 2019

--

Welcome back to this in-depth review of the Pluralsight course Angular Fundamentals, by Joe Eames and Jim Cooper.

In the last episode, I described where this course fits in with the Angular learning path, explained some of the learning options that you have, and summarized the first module. Now we continue with a look at the second module.

There is quite a bit of overlap between the early part of this module and the Angular: Getting Started course, so if you have seen that course you may be able to skim through the first few clips, although the practice exercises may still be useful. I found the second half of this module more informative.

These reviews are intended as supplementary material to the videos themselves. If you are not yet a Pluralsight subscriber and want to know more about it, or if you are interested in getting more out of your Pluralsight subscription, check out Pluralsight: The Definitive Guide.

Jim continues the narration in this second module, and he says this is where it starts to get interesting.

Creating Your First Data-bound Component

The hello world app from the first module is kind of underwhelming. So, in this module we’re going to build something that showcases the power of Angular: a page that shows all of our upcoming Angular-related events.

We start by creating an events-list component, and our first aim is to get it displaying a single event.

import { Component } from ‘@angular/core’;
@Component({

selector: ‘events-list’,
template: `<div>
<h1>Upcoming Angular Events</h1>
</div>

`
})

export class EventsListComponent {

}

We already have an events-app component, which is similar to the above. We change the template line of code in the events-app component to reference our events-list component

<events-list></events-list>

However we have missed something, and when we run it, in the console we see:

Unhandled Promise rejection: Template parse errors:
‘events-list’ is not a known element

When working with Angular we need to register all of our components with our module.

By importing EventListComponent and adding it to our list of declarations in app.module.ts, we solve this problem.

import { EventsListComponent } from ‘./events/events-list.component’

@NgModule{
imports: [ BrowserModule ],
declarations: [ EventsAppComponent, EventsListComponent ],
bootstrap: [ EventsAppComponent ]
})

We then add an object with properties for our event, such as name, date, time, price, and location.

Then Jim introduces us to string interpolation in Angular (you may already have seen this in the Angular: Getting Started course). Interpolation represents a one way binding and we use it to display the event details in our app.

By the end of this clip, this is working, but the component file is quite big and contains our template.

Links to all of the practice exercises are on Jim Cooper’s site.

The practice exercise for Creating a Data-bound Component is here.

Using External Templates

Jim shows us we can move our template html into its own html file, event-list.component.html

In our component definition in our TypeScript file we set the templateUrl property to the URL of our new html file. Our app works just the same as before.

Communicating with Child Components Using @Input

In this clip we start by creating an event-thumbnail component.

This uses most of the markup that we used in the event-list template before, and we cut and paste that into our component.

To say that an event (e.g. a conference) is passed in from another component, we use the @Input decorator.

The practice exercise is here. It is a bit different from the latest video clip because the finished example adds an event-address component instead of an event-thumbnail component. However both the video and the example demonstrate the use of the input decorator.

Communicating with Parent Components Using @Output

We have seen how to pass data from a parent component into a child component with the @Input decorator.

To pass data from a child component back up to the parent component we can use the @Output decorator. We might want to do this if a child component is responding to some event, such as a mouse click on the child component.

In this clip Jim adds a button to the thumbnail component with a binding from a click event to a specified function name:

<button class=”btn btn-primary” (click)=”handleClickMe()”>Click Me!</button>

Jim creates a handleClickMe function inside the event thumbnail component, and defines the eventClick as a new EventEmitter. We need to import the EventEmitter class, which is part of angular/core, into our event thumbnail component.

In your component class add:
@Output() buttonClick = new EventEmitter()

Now practice this yourself.

Using Template Variables to Interact with Child Components

Template reference variables are another way of getting access properties and methods of a child component. We can use them to bind to data on a child component.

We specify a variable name that points to a component, and then we access public properties or methods on it.

<event-thumbnail #thumbnail></event-thumbnail>
<button (click)=”thumbnail.logFoo()”>Log foo</button>

This clip’s demo is more contrived than real world, but it is enough to show the mechanism in action: just click the button to log “foo” to the console

In our eventThumbnail component we call our public logFoo method:

logFoo() { console.log(‘foo’) }

As you can see, this is slightly more simple and straightforward than using input and output parameters.

Jim also demonstrates how to access a component property (called someProperty in this example), and we see the app displaying the value of a property of a child component.

Practice this.

Styling Components

You can easily style a component by adding a styles property to your component and adding the CSS code inside an array.

For example, in our component add:

styles: ['h1 { font-weight: normal; }']

Or use the styleUrls property to reference external style files. List each of your style URLs as strings in an array.

Exploring Angular’s CSS Encapsulation

As your website and your website’s styling grows large, your CSS rules can become difficult to maintain. Even small changes can cause unexpected effects in other areas of your site.

This is because in a typical web application, the style rules in a CSS file get applied to the entire site once that file is loaded.

To avoid this, Jim says it becoming common to use a name spacing type standard such as:

Jim says these techniques can be cumbersome, and that Angular takes care of CSS Encapsulation for us.

We see that styles applied to a child component do not get applied to the parent component. Jim also shows us that styles applied to a parent element do not get automatically inherited by the child component. If you want to apply styles to a child component you can use the ::deep selector (although this is a deprecated feature).

You may be wondering how this is possible, because the CSS specification rules mean rules apply globally. Jim reveals what is going on behind the scenes in this clip (Angular is applying attributes to the elements).

Angular does all the hard work for us applying an architecture that is similar to BEM or SMACSS, taking all the pain of CSS maintainence away from us. In my opinion this is the probably Angular’s best feature.

We can however use global styles in our Angular apps, which is useful if we want to use a UI library such as Bootstrap, Semantic UI, or Angular Material.

Adding a Site Header

Jim rounds off this module by adding a navbar component which works as a header for our site. This is now beginning to look like a real site.

That’s it for this module review, but the course review continue with a look at Angular Template Syntax.

--

--

Kevin O'Shaughnessy

Sr. Full Stack Web Dev promoting better professional practices, tools, solutions & helping others.