# Starters guide to Laravel templates, with Bootstrap

In this guide I will be guiding you through the basic concepts of defining a base layout in Laravel using Blade templates. I will share with you how I after years of working with Laravel choose to structure my layouts. We will be creating our example using Bootstrap, so you have something to continue with after, if you prefer other frameworks such as Tailwind, you should be able to do so, but already knowing the CSS framework would be beneficial then.

I will cover the basic use of Laravel Blade with Bootstrap for a signed in user, you should get the idea afterwards if you wish to create a layout for the landing page as well.

This article is written with Laravel 7 in mind.

## Setup

After you setup your initial Laravel you should use Laravel/UI to install Bootstrap:

1. Install Laravel/UI: `composer require laravel/ui`
2. Prepare Bootstrap: `php artisan ui bootstrap`
3. Install assets: `npm install`

## Structure and core layout

### Worth noting about Laravel Blade

#### Section names
You  can only use a section name once in a structure, this means you are going to have a conflict if you 2 templates uses the same section name:

```html
// Template 1
@yield('content')

// Template2
@extends('Template1')
@section('content')
  @yield('content')
@endsection
```
*** This is prone to errors ! ***

#### Ending sections
A section can be ended by either `@stop` or `@endsection`. Which you choose is up to you, but in my opinion `@endsection` gives you a more readable template.

### Structure
I like to keep my structure as closely related to the one suggested from Laravel, this ensures it's easier for me in the future to go back and modify the code, but also easier for participants to understand my code. Therefor all Blade templates are stored in `/resources/views`. 

Layout  specific templates will be put inside the subdirectory `layout`. Within that I like to keep a subfolder called `parts`, this contains menu, footer, header and other commonly used parts that should be accessible through the various layout templates.

####  Base
Within `layout` create a new file called `base.blade.php`. This is the base template for all templates – but only extended by layout templates.

```html
<!DOCTYPE html>
<html lang="en">
    <head profile="http://www.w3.org/2005/10/profile">
        <meta charset="utf-8">
        <title>My site</title>
        <meta name="app-url" content="{{ url('/') }}">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <link href="{{ url(mix('css/app.css')) }}" rel="stylesheet">
    </head>
    <body>
        @yield('page')
        <script src="{{ url(mix('js/app.js')) }}"></script>
    </body>
</html>
```

#### Blank
Next create a file in `layout` called `blank.blade.php`, this will be the most basic layout. It may seem redundant not just to extend base, but this way we can keep a streamlined architecture and sometimes you might want to force ie a footer to even the minimal layout.

```html
@extends('layout.base')

@section('page')
    @yield('content')
@endsection
```

Also, we ensured the section you later refer to is always `content`.

#### App
For the signed in user the there should be a layout that represents the app view. This will include:

* Navigation
* Header
* App content area

```html
@extends('layout.base')

@section('page')
    @include('layout.parts.navbar')

    <div class="container-fluid">
        <div class="row h-100 mt-3">
            <div class="col">
                @yield('content')
            </div>
        </div>
    </div>
@endsection
```

#### `@include` and `@yield`

We have worked with 2 different ways to work with external template files. The difference is in logic, or direction you might say, they are injected. `@include` is when the template working in knows which external template to inject, such as navigation. This is useful when you have parts of templates that are used in many templates but don't want to rewrite it.

`@yield` is when the template working in, doesn't know the content, this should be more seen as a variable placeholder for child templates to inject content into the parent. (`@section`).

*Not covered here, but useful to add is a global handler for alert and info messages.*

##### Navbar

For our navbar this should be stored in `layouts.parts.navbar`. As the navbar isn't going to have any sub-elements I will just use the default from Bootstrap:

```html
<nav class="navbar navbar-expand-lg navbar-light bg-light">
  <a class="navbar-brand" href="#">Navbar</a>
  <button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarNavAltMarkup" aria-controls="navbarNavAltMarkup" aria-expanded="false" aria-label="Toggle navigation">
    <span class="navbar-toggler-icon"></span>
  </button>
  <div class="collapse navbar-collapse" id="navbarNavAltMarkup">
    <div class="navbar-nav">
      <a class="nav-item nav-link active" href="#">Home <span class="sr-only">(current)</span></a>
      <a class="nav-item nav-link" href="#">Features</a>
    </div>
  </div>
</nav>
```

### Using the layout

#### `@extends`

Now building our content page we can benefit from the layout templates. `@extends` allows to  inherit a parent template sort of how `extends` works for a class in PHP. I  like to put `@extends` at the top of my blade files.

Create the file `/resources/views/content.blade.php` with the following content:

```html
@extends('layouts.app')
```

#### `@section` 

Remember we used `@yield` in the layouts file?  This is referred to as sections in child templates. This means we create a section in the child, which is injected at the yield point in the parent template.

**You should avoid ending up with 2 names that are the same, unless it's unlikely the templates are used together such as for the different layouts**

Make your content site look like this:

```html
@extends('layouts.app')

@section('content')
    <div class="row">
        <div class="col">
             <div class="card">
                 <div class="card-body">
                     My content goes here, both plain text, HTML and Blade syntax.
                 </div>
             </div>
        </div>
    </div>
@endsection
```
