<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Valentine Awe</title>
    <description>The latest articles on DEV Community by Valentine Awe (@valoni01).</description>
    <link>https://dev.to/valoni01</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F648647%2F699057cd-d640-40da-ae75-bea50fb9b83b.jpeg</url>
      <title>DEV Community: Valentine Awe</title>
      <link>https://dev.to/valoni01</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/valoni01"/>
    <language>en</language>
    <item>
      <title>Antenatal for ng new - The mother of all angular applications both dead and alive</title>
      <dc:creator>Valentine Awe</dc:creator>
      <pubDate>Fri, 27 Aug 2021 00:23:09 +0000</pubDate>
      <link>https://dev.to/valoni01/antenatal-for-ng-new-the-mother-of-all-angular-applications-both-dead-and-alive-5dlb</link>
      <guid>https://dev.to/valoni01/antenatal-for-ng-new-the-mother-of-all-angular-applications-both-dead-and-alive-5dlb</guid>
      <description>&lt;p&gt;Before we start, I would like to state that the concepts in this article are not restricted to the Angular framework alone, but can be applied to other frontend frameworks and libraries like Vue and React. &lt;/p&gt;

&lt;h3&gt;
  
  
  Why antenatal?
&lt;/h3&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fgixo3cyr4mfzr0bibhbm.jpeg" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fgixo3cyr4mfzr0bibhbm.jpeg" alt="surprise emoji"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Antenatal in the human world relates to the medical care of women when they are expecting a baby. In our case, &lt;code&gt;ng new&lt;/code&gt; is the mother while our yet be created application is the baby. &lt;/p&gt;

&lt;h3&gt;
  
  
  ng new : The mother of all angular applications dead and alive.
&lt;/h3&gt;

&lt;p&gt;Why this phrase? this is simply because almost all angular applications started with our glorious command &lt;code&gt;ng new&lt;/code&gt;. &lt;code&gt;ng new&lt;/code&gt; has birthed thousands of applications both the ones currently in development, the ones in production, the ones they have stopped using and the ones that never made it to production.&lt;/p&gt;

&lt;p&gt;The whole idea of antenatal is to ensure that complications are avoided during the pregnancy and delivery process. This directly applies to what you need to do before birthing a new application.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;The antenatal care for the &lt;code&gt;ng new&lt;/code&gt; refers to the requirement gathering, research processes, documentation and all that you need to do before you start or create your frontend application.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  Why Should you Care?
&lt;/h3&gt;

&lt;p&gt;Below are some of the reasons why you would need to do the initial research and documentation of your frontend application before spinning up the project. &lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;planning the architecture of your application&lt;/li&gt;
&lt;li&gt;Decision on the numbers of resources needed&lt;/li&gt;
&lt;li&gt;Estimating and managing development time&lt;/li&gt;
&lt;li&gt;Easy maintainability and hand over&lt;/li&gt;
&lt;li&gt;Reduce back and forth with product owners and clients&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;So, whether you are in the consulting space or you work for a specific company, doing this antenatal across all your products makes your development process extra smooth and seamless.&lt;/p&gt;

&lt;h3&gt;
  
  
  Consulting
&lt;/h3&gt;

&lt;p&gt;If you fall under this category, there is a chance that you are going to be involved in different types of projects with unique use cases. And it is important to ask the right questions and document all the specific requirements before you start your application.&lt;/p&gt;

&lt;h3&gt;
  
  
  Company-Specific
&lt;/h3&gt;

&lt;p&gt;If you fall under this category, You may have to do this process once in a while because there may be less frequent changes in your application development processes and policies. But it is also very important to have all these  documented so that new employees or consultants can use them as a reference.&lt;/p&gt;

&lt;p&gt;I have listed below with explanations and examples, some of the research and documentation (antenatal) you need to do before starting a new application. &lt;/p&gt;

&lt;p&gt;It is important to know that this is not a cast in stone. while all the below points are important, you can go ahead and pick the ones that suit your need or you can also add more. &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Application overview&lt;/li&gt;
&lt;li&gt;Application features &lt;/li&gt;
&lt;li&gt;CSS framework&lt;/li&gt;
&lt;li&gt;External libraries&lt;/li&gt;
&lt;li&gt;Device support&lt;/li&gt;
&lt;li&gt;SEO&lt;/li&gt;
&lt;li&gt;Analytics tool&lt;/li&gt;
&lt;li&gt;Software management methodology&lt;/li&gt;
&lt;li&gt;Internationalisation and Localisation &lt;/li&gt;
&lt;li&gt;   Testing&lt;/li&gt;
&lt;li&gt;   Deployment (Staging and Deployment)&lt;/li&gt;
&lt;li&gt;   Communication &lt;/li&gt;
&lt;li&gt;   Documentation&lt;/li&gt;
&lt;li&gt;   Storage&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  1.    Application Overview
&lt;/h3&gt;

&lt;p&gt;This is a detailed explanation of what the product entails  and it should be simple and very easy to understand by anyone who cares to look at the document.&lt;/p&gt;

&lt;h3&gt;
  
  
  2.    Application features
&lt;/h3&gt;

&lt;p&gt;These are the key feature modules in your application. You can derive them from the functional requirement document. Eg. Transaction Management, User, Dashboard, etc. You can further divide this into features module and shared modules. This could help in making decisions around the structure of your application.&lt;/p&gt;

&lt;h3&gt;
  
  
  3.    CSS Framework
&lt;/h3&gt;

&lt;p&gt;The choice of the CSS framework is one of those things that varies across different products especially when you are working in the freelance or consulting space where each client can have their own preference. Examples include bootstrap, angular material, etc. You can also specify the CSS methodology and the CSS preprocessor.&lt;/p&gt;

&lt;h3&gt;
  
  
  4.    External Libraries
&lt;/h3&gt;

&lt;p&gt;These are external libraries apart from the CSS framework. they could range from your charting library, date/time and other critical libraries for company-specific or individual applications. It is important to always keep track of this and it is more useful for people with near static documentation. your consultants or staff will always know the appropriate permissible library to use when starting new projects or adding a new feature that requires an external library.&lt;/p&gt;

&lt;h3&gt;
  
  
  5.    Device support
&lt;/h3&gt;

&lt;p&gt;While it is important to make your application mobile responsive at any point in time. It is also worthy to document the target browsers, resolution information and whether the application has mobile-specific features or views.&lt;/p&gt;

&lt;h3&gt;
  
  
  6.    SEO
&lt;/h3&gt;

&lt;p&gt;Here, you will specify how you want to improve the SEO of your application. You can specify the  strategies. Examples includes server side rendering, dynamic rendering or pre-rendering using tools like &lt;a href="https://scully.io/" rel="noopener noreferrer"&gt;scully&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  7.    Analytics tools And Monitoring
&lt;/h3&gt;

&lt;p&gt;You can further categorize this into different types of environments eg. for local Performance analysis, you can specify tools like the source map explorer. For production monitoring, you can use &lt;a href="https://sentry.io/welcome/" rel="noopener noreferrer"&gt;Sentry&lt;/a&gt; and &lt;a href="https://www.pingdom.com/" rel="noopener noreferrer"&gt;Pingdom&lt;/a&gt; &lt;br&gt;
for traffic, you can use mixpanel, fb, google etc.&lt;/p&gt;

&lt;h3&gt;
  
  
  8.    Software management methodology
&lt;/h3&gt;

&lt;p&gt;Specify the details of the software management methodology. &lt;/p&gt;

&lt;h3&gt;
  
  
  9.    Internationalization and Localization
&lt;/h3&gt;

&lt;p&gt;You need to specify whether there is a need for  internationalization, specify the locals you want to support and the translation tools you are going to use. This is very important as it is easier to implement this during application development. You also need to decide the localization strategy.&lt;/p&gt;

&lt;h3&gt;
  
  
  10.    Testing
&lt;/h3&gt;

&lt;p&gt;You can specify everything about the application testing&lt;br&gt;
eg. The type of testing, test runner (Karma,Cypress), the testing framework (Jasmine,Jest), mocking libraries(Testdouble.js, Jasmine). &lt;/p&gt;

&lt;h3&gt;
  
  
  11.    Deployment
&lt;/h3&gt;

&lt;p&gt;You can define the various deployment strategies and environment. Eg. Whether you will be containerizing your application with tools like Docker, the numbers of environments, server details, type of repositories, AOT or JIT etc.&lt;/p&gt;

&lt;h3&gt;
  
  
  12.    Communication;
&lt;/h3&gt;

&lt;p&gt;This includes things like encryption method, message format. Etc.&lt;/p&gt;

&lt;h3&gt;
  
  
  13.    Storage
&lt;/h3&gt;

&lt;p&gt;This includes general storage information ranging from application local and global storage eg. NGRX, Ankita, Rxjs,NGRX component store, ngrx-slice, session, local, cookies etc. Also, you can include your assets storage.&lt;/p&gt;

&lt;h3&gt;
  
  
  14. Documentation
&lt;/h3&gt;

&lt;p&gt;This is the actual documentation for you angular application. eg. For components libraries documentation you can specify &lt;a href="https://storybook.js.org/" rel="noopener noreferrer"&gt;Story book&lt;/a&gt; and also &lt;a href="https://compodoc.app/index.html" rel="noopener noreferrer"&gt;compodoc&lt;/a&gt; for the angular application documentation &lt;/p&gt;

&lt;h3&gt;
  
  
  Summary
&lt;/h3&gt;

&lt;p&gt;I have outlined what I think are the most critical research or document to put in place before you start any new frontend application. I will gladly love to hear your opinion.&lt;/p&gt;

&lt;p&gt;Here is a repo that shows a possible structure of your document&lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/valoni01/fe-documentation-guide/blob/main/README.md" rel="noopener noreferrer"&gt;Frontend Documentation Guide&lt;/a&gt;&lt;/p&gt;

</description>
      <category>angular</category>
      <category>react</category>
      <category>vue</category>
      <category>architecture</category>
    </item>
    <item>
      <title>Injecting Angular Environment Variables at Build Time</title>
      <dc:creator>Valentine Awe</dc:creator>
      <pubDate>Sun, 15 Aug 2021 15:38:38 +0000</pubDate>
      <link>https://dev.to/valoni01/injecting-angular-environment-variables-at-build-time-84c</link>
      <guid>https://dev.to/valoni01/injecting-angular-environment-variables-at-build-time-84c</guid>
      <description>&lt;p&gt;In this article, I assume that you are containerizing your Angular application and also have a CI/CD process in place. While the example in the article is also AWS specific, you can use the same principle across other cloud services.&lt;/p&gt;

&lt;p&gt;By default, Angular injects the environment variable at the  application build time.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3m1knateh9syigwe29o2.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3m1knateh9syigwe29o2.png" alt="deployment image" width="800" height="167"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The above diagram depicts a regular flow for our application deployment. &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Our frontend app. inclusive of the environment variables 
is pushed to the repo&lt;/li&gt;
&lt;li&gt;Our build process picks it up, builds and deploy to our 
server. &lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;While the above works very well, there are very unique cases where you would be required not to push your environment files to your application repository. If this happens, knowing that angular injects the environment variables at build time, we would need to find a way to inject the environment files during the build process. &lt;/p&gt;

&lt;p&gt;Below are unique reasons why you might be required not to deploy your environment files to your repository&lt;/p&gt;

&lt;p&gt;1.Extra level of security: &lt;br&gt;
    Some companies have policies which prevent them from pushing applications environment variables to their repository whether private repos or not. Although it is worthy to note that the safest way to keep your secret is not to put them in your frontend applications. So, on no account should you place any secret on your Frontend application whether as an environment variable or inside the application.&lt;/p&gt;

&lt;p&gt;2.DevOps flow: &lt;br&gt;
    There are situations where the parameters of your applications can vary based on different environments, while you may know the specifics for an environment file. e.g the dev environment, the production credentials may be required to be added to your application by your devOps team or your client. In order to avoid them making changes to your application or going through a PR flow (which could be necessary depending on your policies). You would want to isolate the environment file from your application.   &lt;/p&gt;

&lt;p&gt;3.Multiple instances with dynamic variables: &lt;br&gt;
    There are scenarios where you would have a single repository for your application but multiple deployment instances that require different configuration files (environment variable). These types of variables could be styles, images, currency type, app settings, base url and many other variables that differ based on each instance. Below is a depiction.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fl8igd6q85gtukrugi2hw.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fl8igd6q85gtukrugi2hw.png" alt="deployment image" width="800" height="361"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;In the Image above, we have a single application repository that is deployed to multiple instances.&lt;/p&gt;

&lt;p&gt;If we follow the flow of having our environment variables in the repository, there would be no way to set different configurations for each of the various instances except we implement the logic of setting variables in the application level based on users, which wouldn't be a 100% perfect solution if we need some configuration on application startup.&lt;/p&gt;

&lt;p&gt;In my experience, I was faced with the three (3) situations above. &lt;/p&gt;
&lt;h2&gt;
  
  
  My Solution
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;Add the environment path to your &lt;code&gt;.gitignore&lt;/code&gt;. this ensures that you do not push your environment files to the repository.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Create a private repo on AWS S3. &lt;br&gt;
a. you can call it (Frontend Env. Variables)&lt;br&gt;
b. Create sub folders for each of your application&lt;br&gt;
c. upload the different environment files. eg (dev, staging and prod)&lt;br&gt;
(In the case of multiple instances with dynamic variables, this should be replicated in each of the environments.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Ensure that our build process has the permission to read from the s3 repository&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Modify the buildSpec file to copy the  file from the s3 repository to the application root folder during the build process.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;h3&gt;
  
  
  s3 folder structure
&lt;/h3&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmgzu0j3fjp5i37xl7eh7.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fmgzu0j3fjp5i37xl7eh7.png" alt="deployment image" width="800" height="361"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h4&gt;
  
  
  Buildspec file
&lt;/h4&gt;


&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt; build:
    commands:
      - echo Build started on `date`
      - printenv
      - aws s3 cp s3://frontend-env-variable/payment- application/ src/ --recursive
      - docker build -t payment-app --build-arg IMAGE_TAG=$IMAGE_TAG .
      - docker images -a
      - echo Building the Docker image...
      - docker tag $APP_NAME:latest $AWS_ACCOUNT_ID.dkr.ecr.eu-west-1.amazonaws.com/$IMAGE_REPO_NAME:$IMAGE_TAG
      - docker images -a
      # - command
  post_build:
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;


&lt;p&gt;Before the docker file is invoked, We already have the environment file copied from the s3 folder to the app folder as seen above in our buildspec file. &lt;/p&gt;

&lt;p&gt;For the multi instance scenario with different environment variables in different cloud instances,&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;Create  separate buildspec files for each environment in your application root. eg. (instance1.buildspec.yml, instance2.buildspec.yml) and each of them will have the reference to the corresponding s3 path.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;In your AWS CDK or codebuild (or whichever build process you have in place, specify the name of the buildspec file for the specific environment&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fg2h7td0ykmdnwu9bgmam.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fg2h7td0ykmdnwu9bgmam.png" alt="deployment image" width="800" height="412"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;With the above process, you can successfully &lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;Deploy your application to the repo without your environment files&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;Have your devOps, client or anyone for each of your business instances that needs to update the environment variables do so.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Just an extra info on what the docker file look file&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;#building angular App
FROM node:14.0.0 as node

WORKDIR /app
COPY package.json /app/
RUN npm install
COPY ./ /app/
ARG IMAGE_TAG=dev
RUN npm run build -- --prod --configuration $IMAGE_TAG

# building nginx
FROM public.ecr.aws/nginx/nginx:1.20-alpine

# FROM nginx:1.12.2-alpine
COPY --from=node /app/dist/payment-app /usr/share/nginx/html
COPY ./nginx-custom.conf /etc/nginx/conf.d/default.conf
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Conclusion&lt;/p&gt;

&lt;p&gt;I believe that there are other fun ways to inject your environment variables at build time. While the above works perfectly for me, I am open to know if you have a differ approach in solving this. &lt;/p&gt;

&lt;p&gt;Remember that this solution is not cloud environment dependent. &lt;/p&gt;

&lt;h3&gt;
  
  
  Do not add any secret to your frontend application
&lt;/h3&gt;

</description>
      <category>aws</category>
      <category>angular</category>
      <category>devops</category>
      <category>docker</category>
    </item>
    <item>
      <title>ngTemplateOutlet</title>
      <dc:creator>Valentine Awe</dc:creator>
      <pubDate>Sun, 08 Aug 2021 13:31:30 +0000</pubDate>
      <link>https://dev.to/valoni01/ng-magical-directives-series-ngtemplateoutlet-2mp1</link>
      <guid>https://dev.to/valoni01/ng-magical-directives-series-ngtemplateoutlet-2mp1</guid>
      <description>&lt;p&gt;"Magic is just science that we do not understand yet" &lt;br&gt;
    ...Arthur C. Clarke&lt;/p&gt;

&lt;p&gt;This article is part of what I call the magical directives series. In this series, we will unravel the mystery behind some interesting Angular directives. Afterwards, we can add this little magic to our tool box. I call them magical directives because they play a very important role in building reusable components across our Angular applications.&lt;/p&gt;

&lt;p&gt;Below are the directives that we will be looking at in this series.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;ng-template&lt;/li&gt;
&lt;li&gt;ng-container&lt;/li&gt;
&lt;li&gt;ng-content&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;*ngTemplateOutlet&lt;/strong&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h6&gt;
  
  
  &lt;strong&gt;links to other articles in this series are below&lt;/strong&gt;
&lt;/h6&gt;
&lt;h1&gt;
  
  
  The ngTemplateOutlet
&lt;/h1&gt;

&lt;p&gt;In our last article &lt;a href="https://dev.to/valoni01/ng-magical-directives-series-ng-content-2gfk"&gt;ng-content&lt;/a&gt;, We said that we are going to discuss the conditional content projection in this particular article. One of the major draw backs in using the &lt;code&gt;ng-content&lt;/code&gt; is the ability to specify default content. What this means is that if a user does not provide the content for a select attribute, that particular content tag will be blank. This is the first problem the &lt;code&gt;*ngTemplateOutlet&lt;/code&gt; helps to solve. The &lt;code&gt;*ngTemplateOutlet&lt;/code&gt; helps to build configurable components and also helps in the insertion of common template in different sessions of our page.&lt;/p&gt;

&lt;p&gt;Let us start with the simple use case for the &lt;code&gt;*ngTemplateOutlet&lt;/code&gt;, which is the insertion of a template into different sessions of our page. for example, if you have a repeated icon across your page, instead of creating the image tag or repeating the host html that holds that image, you can create a template with the &lt;code&gt;&amp;lt;ng-template&amp;gt;&lt;/code&gt; and then use the &lt;code&gt;*ngTemplateOutlet&lt;/code&gt; to reference it in every session that you need to display the icon.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;// Template to be used at multiple sessions in our application

  &amp;lt;ng-template #ourIcon&amp;gt;
     &amp;lt;img src="urImage.jpg" alt="someImge"&amp;gt;
  &amp;lt;/ng-template&amp;gt;

//reference the template across different sessions in our application

  &amp;lt;div&amp;gt;
    &amp;lt;div class="header"&amp;gt;
      &amp;lt;ng-container *ngTemplateOutlet="ourIcon"&amp;gt; &amp;lt;/ng-container&amp;gt;
       &amp;lt;h1&amp;gt;Our lovely page&amp;lt;/h1&amp;gt;
    &amp;lt;/div&amp;gt;

    &amp;lt;div class="body"&amp;gt;
      &amp;lt;ng-container *ngTemplateOutlet="ourIcon"&amp;gt; &amp;lt;/ng-container&amp;gt;
    &amp;lt;/div&amp;gt;

    &amp;lt;div class="Footer"&amp;gt;
      &amp;lt;ng-container *ngTemplateOutlet="ourIcon"&amp;gt; &amp;lt;/ng-container&amp;gt;
    &amp;lt;/div&amp;gt;
  &amp;lt;/div&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the example above, we have been able to use the icon template across multiple sessions in our page without re-writing the html, and if we ever want to change the image url, we just have to update the template without touching the sessions where it is used.&lt;/p&gt;

&lt;h3&gt;
  
  
  The second use case, is for the conditional content projection
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;// books-view.html

&amp;lt;h2&amp;gt;Our Story Books..&amp;lt;/h2&amp;gt;

&amp;lt;ng-container *ngTemplateOutlet="booksTemplate ? booksTemplate : defaultBooks;"&amp;gt;
&amp;lt;/ng-container&amp;gt;

&amp;lt;ng-template #defaultBooks&amp;gt;
  &amp;lt;div *ngFor="let bk of booklist" class="books-card_default"&amp;gt;
    &amp;lt;h1&amp;gt;{{bk.name}}&amp;lt;/h1&amp;gt;
    &amp;lt;p&amp;gt;{{bk.author}}  - {{bk.year}}&amp;lt;/p&amp;gt;
 &amp;lt;/div&amp;gt;
&amp;lt;/ng-template&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  //books.view.ts
  import { Component, Input, OnInit, TemplateRef } from '@angular/core';

@Component({
  selector: 'app-books-view',
  templateUrl: './books-view.component.html',
  styleUrls: ['./books-view.component.scss']
})
export class BooksViewComponent implements OnInit {

  @Input() booksTemplate!:TemplateRef&amp;lt;any&amp;gt;
  @Input() booklist = [
    {name:'The young shall grow', author:'some persons', year:'1975'},
    {name:'Without a silver spoon', author:'some body', year:'1407'},
    {name:'Lara the sugar gurl', author:'everybody',year:'1947'},

  ];

  constructor() { }

  ngOnInit(): void {
  }

}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In sample code above, we have defined a view for our lists of books.&lt;br&gt;
First in the &lt;code&gt;books-view&lt;/code&gt; &lt;code&gt;.ts&lt;/code&gt; file, we are expecting an input of type templateRef&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  @Input() booksTemplate!:TemplateRef&amp;lt;any&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and in the &lt;code&gt;.html&lt;/code&gt; file we defined another template called &lt;code&gt;defaultBooks&lt;/code&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;ng-template #defaultBooks&amp;gt;
  &amp;lt;div *ngFor="let bk of booklist" class="books-card_default"&amp;gt;
    &amp;lt;h1&amp;gt;{{bk.name}}&amp;lt;/h1&amp;gt;
    &amp;lt;p&amp;gt;{{bk.author}}  - {{bk.year}}&amp;lt;/p&amp;gt;
 &amp;lt;/div&amp;gt;
&amp;lt;/ng-template&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;and in our template, we created the template container for the view.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;ng-container *ngTemplateOutlet="booksTemplate ? booksTemplate : defaultBooks;"&amp;gt;
&amp;lt;/ng-container&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is simply saying that, hey! we are expecting an input of type templateRef called booksTemplate, If it is provided, then display it, else use the default defined template called the &lt;code&gt;defaultBooks&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;Now, you can use the &lt;code&gt;books-view&lt;/code&gt; in any part of our application in the following ways.&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;pass in your custom template.
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  &amp;lt;app-books-view [booksTemplate]="myCustomeTemplate"&amp;gt;&amp;lt;/app-books-view&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ol&gt;
&lt;li&gt;Allow the default template to be used
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;  &amp;lt;app-books-view&amp;gt;&amp;lt;/app-books-view&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Unlike the &lt;code&gt;ng-content&lt;/code&gt;, we have been able to provide default values to be projected. &lt;/p&gt;

&lt;p&gt;The &lt;code&gt;*ngTemplateOutlet&lt;/code&gt; is super useful for creating configurable components. &lt;/p&gt;

&lt;h3&gt;
  
  
  Two examples of how we can utilize the power of &lt;code&gt;*ng-templateOutlet&lt;/code&gt; in our books-view
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;&lt;p&gt;create multiple templates for different use cases, eg. card view, table view, list view. e.t.c and allow the parent component that want to use our books-view to specify the type of view they want, else return default view. Here, we can even go further to automate the views depending on defined condition. Example, you can set the &lt;code&gt;hostlistener&lt;/code&gt; to listen to screen sizes, or allow users to select the type of view that they want while you automatically switch between your defined templates (card view, table view, list view). &lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;We can also decide to allow the parent component to send in their own template like we have in the above.&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Below is an example of a parent component using our &lt;code&gt;books-view&lt;/code&gt; along side with customer templates&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;ng-template  #cardView &amp;gt;
   &amp;lt;div let *ngFor="let bk of books" class="books-card"&amp;gt;
      &amp;lt;h1&amp;gt;{{bk.name}}&amp;lt;/h1&amp;gt;
      &amp;lt;p&amp;gt;{{bk.author}}  - {{bk.year}}&amp;lt;/p&amp;gt;
   &amp;lt;/div&amp;gt;
&amp;lt;/ng-template&amp;gt;

&amp;lt;ng-template #tableView &amp;gt;
  &amp;lt;table&amp;gt;
    &amp;lt;tr&amp;gt;
      &amp;lt;th&amp;gt;Title&amp;lt;/th&amp;gt;
      &amp;lt;th&amp;gt;Author&amp;lt;/th&amp;gt;
      &amp;lt;th&amp;gt;Year&amp;lt;/th&amp;gt;
    &amp;lt;/tr&amp;gt;
    &amp;lt;tr *ngFor="let bk of books"&amp;gt;
      &amp;lt;td&amp;gt;{{bk.name}}&amp;lt;/td&amp;gt;
      &amp;lt;td&amp;gt;{{bk.author}}&amp;lt;/td&amp;gt;
      &amp;lt;td&amp;gt;{{bk.year}}&amp;lt;/td&amp;gt;
    &amp;lt;/tr&amp;gt;
  &amp;lt;/table&amp;gt;
&amp;lt;/ng-template&amp;gt;

//passing the template to our app-view
&amp;lt;app-books-view [booksTemplate]="cardView"&amp;gt;&amp;lt;/app-books-view&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;As seen above, we have two templates defined by our parent component, the cardView and the tableView. Although we have manually assigned the cardView to the booksTemplate, but we can always dynamically change the value from the &lt;code&gt;.ts&lt;/code&gt; file of our parent component as discussed earlier.&lt;/p&gt;

&lt;p&gt;Hey guys!.. Isn't that super cool?&lt;/p&gt;

&lt;p&gt;But wait..  If you look at the &lt;code&gt;books-view.ts&lt;/code&gt; you will see that we have default data (booklist) being used. What if we want to send in our own data but still want to use the default template?.&lt;/p&gt;

&lt;p&gt;If you look at the default template, you will notice that it directly has access to the &lt;code&gt;booklist&lt;/code&gt; in our &lt;code&gt;.ts&lt;/code&gt; file. And that is the same for every template embedded in the &lt;code&gt;ng-template&lt;/code&gt; they can access variables in our &lt;code&gt;.ts&lt;/code&gt;. We can further create a unique variable that is only accessible to our template alone and not outside of it. This is done by using &lt;code&gt;let&lt;/code&gt; keyword as in &lt;code&gt;let-[data]&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;ng-container *ngTemplateOutlet="booksTemplate ? booksTemplate : defaultBooks; context:{$implicit:booklist}"&amp;gt;

&amp;lt;/ng-container&amp;gt;

&amp;lt;ng-template let-books #defaultBooks&amp;gt;
  &amp;lt;div *ngFor="let bk of books" class="books-card_default"&amp;gt;
    &amp;lt;h1&amp;gt;{{bk.name}}&amp;lt;/h1&amp;gt;
    &amp;lt;p&amp;gt;{{bk.author}}  - {{bk.year}}&amp;lt;/p&amp;gt;
 &amp;lt;/div&amp;gt;
&amp;lt;/ng-template&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Here, we have defined a variable books that is only accessible by our template, we no longer have direct access to the &lt;code&gt;booklist&lt;/code&gt; in our &lt;code&gt;.ts&lt;/code&gt;. Where does the &lt;code&gt;let-books&lt;/code&gt; get its value from?&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;The data for the let-books can be gotten directly from the parent&lt;/li&gt;
&lt;li&gt;&lt;p&gt;From a default value set in the &lt;code&gt;*ngTemplateOutlet&lt;/code&gt; &lt;code&gt;context&lt;/code&gt; property&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;To get the value from the parent&lt;br&gt;
&lt;/p&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt; &amp;lt;app-books-view [booklist]='booklist'&amp;gt;&amp;lt;/app-books-view&amp;gt; 
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Here, we are are not passing any template to the books views, this means that we want to use the default template while we are sending our own data to the template. Now, what happens is that&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Our &lt;code&gt;books-views&lt;/code&gt; will first check if booklist has been passed as an input value.&lt;/li&gt;
&lt;li&gt;If the value is passed, it then assign the value of the &lt;code&gt;booklist&lt;/code&gt; to &lt;code&gt;let-books&lt;/code&gt; through the context&lt;/li&gt;
&lt;li&gt;If there is no &lt;code&gt;booklist&lt;/code&gt; passed to it, it then assign the data specified in the context to the &lt;code&gt;let-books&lt;/code&gt;. &lt;code&gt;context:{$implicit:booklist}&lt;/code&gt; which is the default value.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;This way, we can successfully send in our own data to &lt;code&gt;books-view&lt;/code&gt; while still using the default template.&lt;/p&gt;

&lt;p&gt;Same way, if we want to send in our custom template and also allow for dynamic data, we can also declare the template scoped variable with the &lt;code&gt;let&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;In our parent component&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;ng-template let-books #cardView &amp;gt;
   &amp;lt;div let *ngFor="let bk of books" class="books-card"&amp;gt;
      &amp;lt;h1&amp;gt;{{bk.name}}&amp;lt;/h1&amp;gt;
      &amp;lt;p&amp;gt;{{bk.author}}  - {{bk.year}}&amp;lt;/p&amp;gt;
   &amp;lt;/div&amp;gt;
&amp;lt;/ng-template&amp;gt;

&amp;lt;ng-template let-books #tableView &amp;gt;
  &amp;lt;table&amp;gt;
    &amp;lt;tr&amp;gt;
      &amp;lt;th&amp;gt;Title&amp;lt;/th&amp;gt;
      &amp;lt;th&amp;gt;Author&amp;lt;/th&amp;gt;
      &amp;lt;th&amp;gt;Year&amp;lt;/th&amp;gt;
    &amp;lt;/tr&amp;gt;
    &amp;lt;tr *ngFor="let bk of books"&amp;gt;
      &amp;lt;td&amp;gt;{{bk.name}}&amp;lt;/td&amp;gt;
      &amp;lt;td&amp;gt;{{bk.author}}&amp;lt;/td&amp;gt;
      &amp;lt;td&amp;gt;{{bk.year}}&amp;lt;/td&amp;gt;
    &amp;lt;/tr&amp;gt;
  &amp;lt;/table&amp;gt;
&amp;lt;/ng-template&amp;gt;

&amp;lt;!-- This allows you to use project your custom template and also pass in the data.   --&amp;gt;
&amp;lt;app-books-view [booklist]='booklist'  [booksTemplate]="cardView"&amp;gt;&amp;lt;/app-books-view&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Here, we have also added the &lt;code&gt;let-books&lt;/code&gt; variable to our custom templates. Whenever we pass in the data to our template, it assigns the value of the data to our context&lt;br&gt;
whose value is then assigned to the &lt;code&gt;let-books&lt;/code&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;app-books-view [booklist]='booklist'  [booksTemplate]="cardView"&amp;gt;&amp;lt;/app-books-view&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can check out the github rep for the sample code above&lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/valoni01/ng-magical-directives"&gt;https://github.com/valoni01/ng-magical-directives&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Conclusion
&lt;/h2&gt;

&lt;p&gt;you can utilize the magical power of the &lt;code&gt;*ngTemplateOutlet&lt;/code&gt;, &lt;code&gt;ng-template&lt;/code&gt;, &lt;code&gt;ng-content&lt;/code&gt; and &lt;code&gt;ng-container&lt;/code&gt; to create your own reusable component library while also giving your users the flexibility to customize the components.&lt;/p&gt;

&lt;p&gt;Previous: &lt;a href="https://dev.to/valoni01/ng-magical-directives-series-ng-content-2gfk"&gt;ng-content&lt;/a&gt;&lt;/p&gt;

</description>
      <category>angular</category>
      <category>typescript</category>
    </item>
    <item>
      <title>ng-content</title>
      <dc:creator>Valentine Awe</dc:creator>
      <pubDate>Sun, 25 Jul 2021 11:09:07 +0000</pubDate>
      <link>https://dev.to/valoni01/ng-magical-directives-series-ng-content-2gfk</link>
      <guid>https://dev.to/valoni01/ng-magical-directives-series-ng-content-2gfk</guid>
      <description>&lt;p&gt;"Magic is just science that we do not understand yet" &lt;br&gt;
    ...Arthur C. Clarke&lt;/p&gt;

&lt;p&gt;This article is part of what I call the magical directives series. In this series, we will unravel the mystery behind some interesting Angular directives. Afterwards, we can add this little magic to our tool box. I call them magical directives because they play a very important role in building reusable components across our Angular applications.&lt;/p&gt;

&lt;p&gt;Below are the directives that we will be looking at in this series.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;ng-template&lt;/li&gt;
&lt;li&gt;ng-container&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;ng-content&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;*ngTemplateOutlet&lt;/li&gt;
&lt;/ul&gt;
&lt;h6&gt;
  
  
  &lt;strong&gt;links to other articles in this series are below&lt;/strong&gt;
&lt;/h6&gt;
&lt;h1&gt;
  
  
  The ng-content
&lt;/h1&gt;

&lt;p&gt;The &lt;code&gt;ng-content&lt;/code&gt; is used to create configurable components. If we use the &lt;code&gt;ng-content&lt;/code&gt; tag in our template, the inner content of the tags that define our component are then projected into this space.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;//app-modal.html

&amp;lt;div&amp;gt;
  &amp;lt;div class="header"&amp;gt; Amazing Header &amp;lt;/div&amp;gt;
  &amp;lt;div class="body"&amp;gt;
     &amp;lt;p&amp;gt; Hi Friends! How are you today &amp;lt;/p&amp;gt;
  &amp;lt;/div&amp;gt;
  &amp;lt;div class="footer"&amp;gt;This is our footer&amp;lt;/div&amp;gt;
&amp;lt;div&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The sample code above represents a modal. If there is a need to have this modal in multiple places in our application with different styles/content in the body, it means that we will have to create more modals for each of the use cases. This is not a problem for small apps. But imagine when you have to use similar modal in over 5 different places or more with dynamic content in the body. This is where the magical effects of &lt;code&gt;ng-content&lt;/code&gt; comes to our aid.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;//app-modal.html

&amp;lt;div&amp;gt;
  &amp;lt;div class="header"&amp;gt; Amazing Header &amp;lt;/div&amp;gt;
  &amp;lt;div class="body"&amp;gt;
    &amp;lt;ng-content&amp;gt; &amp;lt;/ng-content&amp;gt;
  &amp;lt;/div&amp;gt;
  &amp;lt;div class="footer"&amp;gt;This is our footer&amp;lt;/div&amp;gt;
&amp;lt;div&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the sample code above, instead of hardcoding the content of the body, we used the &lt;code&gt;&amp;lt;ng-content&amp;gt; &amp;lt;/ng-content&amp;gt;&lt;/code&gt; tag. &lt;br&gt;
If other components wants to use the &lt;code&gt;app-modal&lt;/code&gt; component with a custom body, the components will project the content inside the &lt;code&gt;app-modal&lt;/code&gt; and the content projected will be positioned in the place where we have specified the &lt;code&gt;ng-content&lt;/code&gt; tag in the &lt;code&gt;app-modal&lt;/code&gt; as seen below.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;//app-parent.html

&amp;lt;app-modal&amp;gt; 
   &amp;lt;div&amp;gt;
      &amp;lt;h3&amp;gt; My body intro. &amp;lt;/h3&amp;gt;
      &amp;lt;p&amp;gt; The perfect paragraph &amp;lt;/p&amp;gt;
   &amp;lt;/div&amp;gt;
&amp;lt;/app-modal&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Instead of creating multiple modals for different use cases across our application, we are now able to create a single modal component that allows us to project whatever content we want in the body. This process is referred to as &lt;code&gt;Content projection&lt;/code&gt;. With this, we can build reusable components for a single project or a reusable component library for all our projects. &lt;/p&gt;

&lt;p&gt;There are three types of content projection&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Single-slot content projection&lt;/li&gt;
&lt;li&gt;Multiple-slot content projection&lt;/li&gt;
&lt;li&gt;Conditional content projection&lt;/li&gt;
&lt;/ol&gt;

&lt;h5&gt;
  
  
  In order to keep our article dry, We will discuss the conditional content projection in the last session of this series &lt;a href="https://dev.to/valoni01/ng-magical-directives-series-ngtemplateoutlet-2mp1"&gt;*ngTemplateOutlet&lt;/a&gt;
&lt;/h5&gt;

&lt;p&gt;The first example above covers the single-slot content projection, where we were only required to project a single dynamic content. What happens if the content of the header and footer are also dynamic?&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;//app-modal.html

&amp;lt;div&amp;gt;
  &amp;lt;ng-content&amp;gt; &amp;lt;/ng-content&amp;gt;
  &amp;lt;div class="body"&amp;gt;
    &amp;lt;ng-content&amp;gt; &amp;lt;/ng-content&amp;gt;
  &amp;lt;/div&amp;gt;
  &amp;lt;ng-content&amp;gt; &amp;lt;/ng-content&amp;gt;
&amp;lt;div&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In this case, Angular is going to scream &lt;em&gt;Wooooooooh&lt;/em&gt;. Because Angular wouldn't know the exact place to project the content that we are trying to project. The multiple-slot content projection comes to our rescue.&lt;/p&gt;

&lt;h1&gt;
  
  
  Multiple-Slot Content Projection
&lt;/h1&gt;

&lt;p&gt;The multiple-slot content projection is what allows us to project multiple dynamic content to our component. The &lt;code&gt;ng-content&lt;/code&gt; provides us with the &lt;code&gt;select&lt;/code&gt; attribute that allows us to specify an identifier for a specific &lt;code&gt;ng-content&lt;/code&gt; tag. Below are various ways in which we can achieve this with different selectors.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;//app-modal.html

&amp;lt;div&amp;gt;
  &amp;lt;ng-content select=".header"&amp;gt; &amp;lt;/ng-content&amp;gt;
  &amp;lt;div class="body"&amp;gt;
    &amp;lt;ng-content select="#body"&amp;gt; &amp;lt;/ng-content&amp;gt;
  &amp;lt;/div&amp;gt;
  &amp;lt;ng-content select="span"&amp;gt; &amp;lt;/ng-content&amp;gt;
&amp;lt;div&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Here, we have specified unique selectors for each content that needs to be projected. anytime we want to reuse this modal component, we just need to ensure that we specify a class with the name header, a body with an id of body and also a span tag. When Angular sees this, it will automatically know where to position or project the content that you have projected as seen in the example below.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;//app-parent.html

&amp;lt;app-modal&amp;gt; 
   &amp;lt;div class="header"&amp;gt; Our header &amp;lt;/div&amp;gt;
   &amp;lt;div id="body"&amp;gt;
      &amp;lt;h3&amp;gt; My body intro. &amp;lt;/h3&amp;gt;
      &amp;lt;p&amp;gt; The perfect paragraph &amp;lt;/p&amp;gt;
   &amp;lt;/div&amp;gt;
   &amp;lt;span&amp;gt; The footer&amp;lt;/span&amp;gt;
&amp;lt;/app-modal&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;NOTE: If for some reasons there is an &lt;code&gt;ng-content&lt;/code&gt; tag without an identifier (select), it will automatically serves as a default projector for any content that has no identifier.&lt;/p&gt;

&lt;p&gt;Other examples of multiple-slot content projection&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt; //app-modal.html
 &amp;lt;div&amp;gt;
   &amp;lt;ng-content select="[slot=head]"&amp;gt;&amp;lt;/ng-content&amp;gt;
   &amp;lt;ng-content select="[slot=body]"&amp;gt;&amp;lt;/ng-content&amp;gt;
   &amp;lt;ng-content select="[slot=footer]"&amp;gt;&amp;lt;/ng-content&amp;gt;
 &amp;lt;/div&amp;gt;

//app-parent.html
&amp;lt;app-modal&amp;gt;
   &amp;lt;div slot="head"&amp;gt; Our header &amp;lt;/div&amp;gt;
   &amp;lt;div slot="body"&amp;gt; Our body &amp;lt;/div&amp;gt;
   &amp;lt;div slot="footer"&amp;gt; Our footer &amp;lt;/div&amp;gt;
&amp;lt;/app-modal&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt; //app-modal.html
 &amp;lt;div&amp;gt;
   &amp;lt;ng-content select="[head]"&amp;gt;&amp;lt;/ng-content&amp;gt;
   &amp;lt;ng-content select="[body]"&amp;gt;&amp;lt;/ng-content&amp;gt;
   &amp;lt;ng-content select="[footer]"&amp;gt;&amp;lt;/ng-content&amp;gt;
 &amp;lt;/div&amp;gt;

//app-parent.html
&amp;lt;app-modal&amp;gt;
   &amp;lt;div head&amp;gt; Our header &amp;lt;/div&amp;gt;
   &amp;lt;div body&amp;gt; Our body &amp;lt;/div&amp;gt;
   &amp;lt;div footer&amp;gt; Our footer &amp;lt;/div&amp;gt;
&amp;lt;/app-modal&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;you can also use custom components tags/selectors.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt; //app-modal.html
 &amp;lt;div&amp;gt;
   &amp;lt;ng-content select="app-head"&amp;gt;&amp;lt;/ng-content&amp;gt;
   &amp;lt;ng-content select="app-body"&amp;gt;&amp;lt;/ng-content&amp;gt;
   &amp;lt;ng-content select="app-footer"&amp;gt;&amp;lt;/ng-content&amp;gt;
 &amp;lt;/div&amp;gt;

//app-parent.html
&amp;lt;app-modal&amp;gt;
   &amp;lt;app-head&amp;gt; Our header &amp;lt;/app-head&amp;gt;
   &amp;lt;app-body&amp;gt; Our body &amp;lt;/app-body&amp;gt;
   &amp;lt;app-footer&amp;gt; Our footer &amp;lt;/app-footer&amp;gt;
&amp;lt;/app-modal&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h1&gt;
  
  
  Summary
&lt;/h1&gt;

&lt;p&gt;With the &lt;code&gt;ng-content&lt;/code&gt; You can build your own reusable components without you worrying about the contents or the styles of the contents the users needs to project.&lt;/p&gt;

&lt;p&gt;Previous: &lt;a href="https://dev.to/valoni01/ng-magical-directives-series-ng-container-2979"&gt;ng-container&lt;/a&gt;&lt;br&gt;
Next: &lt;a href="https://dev.to/valoni01/ng-magical-directives-series-ngtemplateoutlet-2mp1"&gt;*ngTemplateOutlet&lt;/a&gt;  &lt;/p&gt;

</description>
      <category>angular</category>
      <category>directives</category>
      <category>typescript</category>
      <category>contentprojection</category>
    </item>
    <item>
      <title>ng-container</title>
      <dc:creator>Valentine Awe</dc:creator>
      <pubDate>Sun, 20 Jun 2021 11:56:07 +0000</pubDate>
      <link>https://dev.to/valoni01/ng-magical-directives-series-ng-container-2979</link>
      <guid>https://dev.to/valoni01/ng-magical-directives-series-ng-container-2979</guid>
      <description>&lt;p&gt;"Magic is just science that we do not understand yet" &lt;br&gt;
    ...Arthur C. Clarke&lt;/p&gt;

&lt;p&gt;This article is part of what I call the magical directives series. In this series, we will unravel the mystery behind some interesting Angular directives. Afterwards, we can add this little magic to our tool box. I call them magical directives because they play a very important role in building reusable components across our Angular applications.&lt;/p&gt;

&lt;p&gt;Below are the directives that we will be looking at in this series.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;ng-template&lt;/li&gt;
&lt;li&gt;&lt;strong&gt;ng-container&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;ng-content&lt;/li&gt;
&lt;li&gt;*ngTemplateOutlet&lt;/li&gt;
&lt;/ul&gt;
&lt;h6&gt;
  
  
  &lt;strong&gt;links to other articles in this series are below&lt;/strong&gt;
&lt;/h6&gt;
&lt;h1&gt;
  
  
  The ng-container
&lt;/h1&gt;

&lt;p&gt;The &lt;code&gt;ng-container&lt;/code&gt; is a grouping element that does not introduce a new element in the DOM when used in our template. This means that it does not interfere with the layout and style of your application. &lt;/p&gt;

&lt;p&gt;The &lt;code&gt;ng-container&lt;/code&gt; is mostly used with the structural directives. However, it serves two major purposes:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Removal of redundant elements &lt;/li&gt;
&lt;li&gt;Elimination of invalid HTML code&lt;/li&gt;
&lt;/ol&gt;
&lt;h2&gt;
  
  
  Removal of Redundant Elements
&lt;/h2&gt;

&lt;p&gt;I am pretty sure that almost every Angular developer at some point in their learning stage encountered the below error&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F29teiw8t53q4zkxjpk7w.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F29teiw8t53q4zkxjpk7w.png" alt="code sample"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The error is very clear, and it is because we are trying to use two structural directives on the same element. Below is the most common way we try to resolve the error.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fyy95mi1kvuv2324ymsry.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fyy95mi1kvuv2324ymsry.png" alt="sample code"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Well, while this is a very smart way to get rid of the error, there is a smarter way. Before we move forward, let us take a look at what is wrong with the above method of resolving the error.&lt;/p&gt;

&lt;p&gt;Firstly, carefully look at the DOM below. You will notice that there is an empty &lt;code&gt;div&lt;/code&gt; before the actual &lt;code&gt;div&lt;/code&gt; that holds our values. This extra div has no purpose in our code, which makes it  redundant. Also, this solution does not give you a cleaner DOM tree and depending on the structure of your template you may have to nest your styles in order to style the content of your target &lt;code&gt;div&lt;/code&gt; i.e the div that holds the value.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F2hkxjklgyz4vcvh6teso.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F2hkxjklgyz4vcvh6teso.png" alt="sample code"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;This is where the &lt;code&gt;ng-container&lt;/code&gt; comes into play. Remember we said that the &lt;code&gt;ng-container&lt;/code&gt; does not interfere with the layout and style of you application, because it does not introduce a new element. If we replace our redundant &lt;code&gt;div&lt;/code&gt; with the &lt;code&gt;ng-container&lt;/code&gt;, below is what we will get when we inspect the DOM&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fv7ekn6ydv6cooht38t8p.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fv7ekn6ydv6cooht38t8p.png" alt="sample code"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fjvc775yrlyive14x12yr.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fjvc775yrlyive14x12yr.png" alt="sample code"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Isn't that cool?. &lt;/p&gt;

&lt;p&gt;Another example is using the &lt;code&gt;ng-container&lt;/code&gt; to replace inline elements, which also helps to remove redundant elements and make your styling easier.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;div&amp;gt;
   &amp;lt;span&amp;gt; 
      The world is incomplete without you 
   &amp;lt;/span&amp;gt;
&amp;lt;/div&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the code sample above, we have redundant inline element &lt;code&gt;span&lt;/code&gt; which just holds a value. We can use the &lt;code&gt;ng-container&lt;/code&gt; to eliminate the span by replacing the &lt;code&gt;span&lt;/code&gt; with the &lt;code&gt;ng-container&lt;/code&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;div&amp;gt;
   &amp;lt;ng-container&amp;gt;
      The world is incomplete without you
   &amp;lt;/ng-container&amp;gt;
&amp;lt;/div&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now, If you check the DOM tree, It will exactly look like what we have below&lt;/p&gt;

&lt;p&gt;&lt;code&gt;&amp;lt;div&amp;gt; The world is incomplete without you &amp;lt;/div&amp;gt;&lt;/code&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Eliminating invalid HTML
&lt;/h2&gt;

&lt;p&gt;There are sometimes when we make little mistakes in our template without even knowing. But because the browser is our friend, it does a lot of cleaning up for us so that our mistakes do not reflect on our web pages. A typical example is this.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;ul&amp;gt;
  &amp;lt;div *ngFor="let hero of Heroes"&amp;gt;
    &amp;lt;li *ngIf="hero.name !== 'val'"&amp;gt;
      {{ hero.powers }}
    &amp;lt;/li&amp;gt;
  &amp;lt;/div&amp;gt;
&amp;lt;/ul&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the above, we used a &lt;code&gt;div&lt;/code&gt; inside a list. The browser will ignore this and will successfully render our template without throwing any error. There are many other scenarios where we might be tempted to do something similar in order to get our logic right, but this is not good practice. The &lt;code&gt;ng-container&lt;/code&gt; comes in very handy again in eliminating this. see sample code below&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;ul&amp;gt;
  &amp;lt;ng-container *ngFor="let hero of Heroes"&amp;gt;
    &amp;lt;li *ngIf="hero.name !== 'val'"&amp;gt;
      {{ hero.powers }}
    &amp;lt;/li&amp;gt;
  &amp;lt;/ng-container&amp;gt;
&amp;lt;/ul&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;With this, if you inspect your DOM, you will notice that you have your list without the interference of any other element as seen with the previous example when we had the DIV.&lt;/p&gt;

&lt;h1&gt;
  
  
  Summary
&lt;/h1&gt;

&lt;p&gt;With &lt;code&gt;ng-container&lt;/code&gt;, we are sure of having cleaner style sheet and elimination of redundant HTML elements across our applications.&lt;/p&gt;

&lt;p&gt;Previous: &lt;a href="https://dev.to/valoni01/ng-magical-directives-series-ng-template-41n"&gt;ng-template&lt;/a&gt;&lt;br&gt;
Next: &lt;a href="https://dev.to/valoni01/ng-magical-directives-series-ng-content-2gfk"&gt;ng-content&lt;/a&gt;&lt;/p&gt;

</description>
      <category>angular</category>
      <category>typescript</category>
      <category>javascript</category>
      <category>directives</category>
    </item>
    <item>
      <title>ng-template</title>
      <dc:creator>Valentine Awe</dc:creator>
      <pubDate>Sun, 13 Jun 2021 16:33:05 +0000</pubDate>
      <link>https://dev.to/valoni01/ng-magical-directives-series-ng-template-41n</link>
      <guid>https://dev.to/valoni01/ng-magical-directives-series-ng-template-41n</guid>
      <description>&lt;blockquote&gt;
&lt;p&gt;Magic is just science that we do not understand yet&lt;br&gt;
    &lt;em&gt;...Arthur C. Clarke&lt;/em&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;This article is part of what I call the magical directives series. In this series, we will unravel the mystery behind some interesting Angular directives. Afterwards, we can add this little magic to our tool box. I call them magical directives because they play a very important role in building reusable components across our Angular applications.&lt;/p&gt;

&lt;p&gt;Below are the directives that we will be looking at in this series.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;strong&gt;ng-template&lt;/strong&gt;&lt;/li&gt;
&lt;li&gt;ng-container&lt;/li&gt;
&lt;li&gt;ng-content&lt;/li&gt;
&lt;li&gt;*ngTemplateOutlet&lt;/li&gt;
&lt;/ul&gt;

&lt;h1&gt;
  
  
  The ng-template
&lt;/h1&gt;

&lt;p&gt;The &lt;em&gt;ng-template&lt;/em&gt; directive simply represent an Angular template. Angular uses the ng-template under the hood in our structural directives( &lt;a href="https://angular.io/api/common/NgIf" rel="noopener noreferrer"&gt;&lt;strong&gt;*ngIf&lt;/strong&gt;&lt;/a&gt;, &lt;a href="https://angular.io/api/common/NgForOf" rel="noopener noreferrer"&gt;&lt;strong&gt;*ngFor&lt;/strong&gt;&lt;/a&gt;) and &lt;a href="https://angular.io/api/common/NgSwitch" rel="noopener noreferrer"&gt;&lt;strong&gt;ngSwitch&lt;/strong&gt;&lt;/a&gt;. The &lt;em&gt;ngSwitch&lt;/em&gt; controls the structural directives (&lt;a href="https://angular.io/api/common/NgSwitchCase" rel="noopener noreferrer"&gt;*ngSwitchCase&lt;/a&gt; and &lt;a href="https://angular.io/api/common/NgSwitchDefault" rel="noopener noreferrer"&gt;*ngSwitchDefault&lt;/a&gt; ) and it is an attribute directive. &lt;/p&gt;

&lt;p&gt;Whenever we use any of these structural directives, Angular does the below.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;!-- Your actual code with a structural directive --&amp;gt;

&amp;lt;div *ngIf="food"&amp;gt;
  &amp;lt;p&amp;gt;some interesting contents&amp;lt;/p&amp;gt;
&amp;lt;div&amp;gt;

&amp;lt;!-- What Angular does behind the scene--&amp;gt;

&amp;lt;ng-template [ngIf]="food"&amp;gt;
  &amp;lt;div&amp;gt;
    &amp;lt;p&amp;gt;some interesting contents&amp;lt;/p&amp;gt;
  &amp;lt;/div&amp;gt;
&amp;lt;/ng-template&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;From the above code sample, Angular sees the &lt;code&gt;asterisk (*)&lt;/code&gt; in the &lt;code&gt;*ngIf&lt;/code&gt; and automatically recognizes it as a structural directive. It then wraps the host element inside an &lt;code&gt;ng-template&lt;/code&gt;, this is the same for other structural directives. What makes it more beautiful is that, Angular comments the &lt;code&gt;ng-template&lt;/code&gt; directive (as seen in green text in the image below), so the &lt;em&gt;ng-template&lt;/em&gt; is never displayed as a tag in the DOM tree.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F49ykq57vjcjmc8oo29su.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F49ykq57vjcjmc8oo29su.png" alt="image"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h6&gt;
  
  
  NB: Angular does not display the content of the ng-template by default. The ng-template only represents a template which you can then decide how you want it to be displayed.
&lt;/h6&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fiqcx1fon7wevgiwm7a0o.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fiqcx1fon7wevgiwm7a0o.png" alt="image"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h6&gt;
  
  
  &lt;em&gt;From the image above, Angular converts the &lt;code&gt;*&lt;/code&gt; into an ng-template which then result to a nested ng-template. Since Angular does not display the content of the ng-template, We will end up with just comments&lt;/em&gt;
&lt;/h6&gt;

&lt;p&gt;If you decide to write your structural directives inside the ng-template, you will just have to replicate what Angular does when it sees a structural directive. E.g for &lt;code&gt;*ngIf&lt;/code&gt;, it will be &lt;code&gt;&amp;lt;ng-template [*ngIf]=""&amp;gt; &amp;lt;/ng-template&amp;gt;&lt;/code&gt; As seen in the first code sample above. You can do the same for other structural directives and it will work just fine. Below is an example with ngSwitch.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;!-- ngSwtich with structural directives *ngSwitchCase and *ngSwitchDefault --&amp;gt;

&amp;lt;div [ngSwitch]="food"&amp;gt;
    &amp;lt;div *ngSwitchCase="'Beans'"&amp;gt; yeah... Sweet Beans&amp;lt;/div&amp;gt;
    &amp;lt;div *ngSwitchCase="'Rice'"&amp;gt; ummm.. Yummy rice&amp;lt;/div&amp;gt;
    &amp;lt;div *ngSwitchDefault&amp;gt;No Food Selected&amp;lt;/div&amp;gt;
&amp;lt;/div&amp;gt;

&amp;lt;!-- ngSwitch with ng-template  --&amp;gt;

&amp;lt;div [ngSwitch]="food"&amp;gt;
    &amp;lt;ng-template [ngSwitchCase]="'Beans'"&amp;gt; yeah... Sweet Beans&amp;lt;/ng-template&amp;gt;
    &amp;lt;ng-template [ngSwitchCase]="'Rice'"&amp;gt; ummm.. Yummy rice&amp;lt;/ng-template&amp;gt;
    &amp;lt;ng-template ngSwitchDefault&amp;gt;No Food Selected&amp;lt;/ng-template&amp;gt;
&amp;lt;/div&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Using the ng-template can help remove redundant elements from your DOM tree when necessary. As seen in the code sample with the &lt;em&gt;ngSwtich&lt;/em&gt; and &lt;em&gt;ng-template&lt;/em&gt;, there won't be an extra &lt;code&gt;div&lt;/code&gt; created in the DOM tree compare to the first sample without the ng-template. Although, it could sometimes be easier and cleaner in most cases to use the &lt;code&gt;*&lt;/code&gt; i.e instead of wrapping the host inside the ng-template.&lt;/p&gt;

&lt;p&gt;But wait, there are other interesting ways that you can utilize the magical effect of the &lt;em&gt;ng-template&lt;/em&gt; and one of them is with the &lt;strong&gt;ngIf-else&lt;/strong&gt; and &lt;strong&gt;ngIf-else-then&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Let us take for instance that you are working on an application where you want to display a certain template based on a condition. In this case, you can enclose the templates in an &lt;em&gt;ng-template&lt;/em&gt; and add a reference to each template so that whenever a certain condition is met, the corresponding template will be displayed as seen in the image below.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fix69vm6e33kixltunamx.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fix69vm6e33kixltunamx.png" alt="image"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;A common use case is when you are waiting for a response from the server and you want to temporary display a loader until you receive the response.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;!-- use case for If else --&amp;gt;
&amp;lt;div *ngIf="result else loading"&amp;gt;
   &amp;lt;p&amp;gt;{{result}}&amp;lt;/p&amp;gt;
&amp;lt;/div&amp;gt;


&amp;lt;!-- our loader template --&amp;gt;

&amp;lt;ng-template #loading&amp;gt;
    Loading ...
&amp;lt;/ng-template&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;em&gt;Here, the default display will be 'Loading..' until we get the result from the server.&lt;/em&gt;&lt;/p&gt;

&lt;h1&gt;
  
  
  Summary
&lt;/h1&gt;

&lt;p&gt;The magical effects of the ng-template cannot be over emphasized. In the rest of the series, we will see how to use the ng-template along with the other directives.&lt;/p&gt;

&lt;p&gt;Next: &lt;a href="https://dev.to/valoni01/ng-magical-directives-series-ng-container-2979"&gt;ng-container&lt;/a&gt;&lt;/p&gt;

</description>
      <category>angular</category>
      <category>directives</category>
      <category>javascript</category>
      <category>typescript</category>
    </item>
  </channel>
</rss>
