Skip to main content

Interfaces

By default, Flute uses the BladeOne templating engine, which is identical to Laravel's Blade, so if you're not familiar with it, I recommend getting acquainted.

How Interfaces Work

Let me explain how interfaces work. Each request renders a single template (home.blade.php), which provides us with the sidebar, navbar, and all meta tags. But how does it do this? It's unlikely that we need to specify all of this in every module.

Yes, each template uses @extends() of the main template. Essentially, the template does not render content but adds content to another template, which will be rendered.

I understand it might be difficult, so let's get to practice quickly. Let's see the standard layout template:

layout.blade.php
@cookie_alert
@lang_alert

<!DOCTYPE html>
<html lang="{{ app()->getLang() }}" data-theme="dark">

<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<link rel="icon" type="image/x-icon" href="@asset('favicon.ico')">
<title>@yield('title', page()->title)</title>

<meta name="csrf-token" content="{{ csrf_token() }}">
<meta name="description" content="{{ page()->description }}">
<meta name="keywords" content="{{ page()->keywords }}">
<meta name="robots" content="{{ page()->robots }}">
<meta property="og:title" content="{{ page()->og_title }}">
<meta property="og:description" content="{{ page()->og_description }}">
<meta property="og:image" content="{{ page()->og_image }}">

<link rel='stylesheet' href='@asset('montserrat')' type='text/css'>
<link rel='stylesheet' href='@asset('sfpro')' type='text/css'>
<link rel="stylesheet" href="@asset('animate')" type='text/css'>
<link rel="stylesheet" href="@asset('grid')" type='text/css'>
<link rel="stylesheet" href="@asset('assets/css/libs/driver.css')">

<script src="@asset('phosphor')"></script>

@at(tt('assets/styles/main.scss'))

@stack('header')
</head>

<body>
<main>
@stack('content')
</main>
<footer>
<script src="@asset('jquery')"></script>
<script src="@asset('assets/js/sweetalert.js')"></script>
<script src="@asset('assets/js/driver.js')"></script>
<script src="@asset('assets/js/forms.js')"></script>
<script src="@asset('assets/js/app.js')"></script>


@at(tt('assets/js/modal.js'))
@at(tt('assets/js/template.js'))

@stack('footer')
</footer>
<div class="toast-container">
@stack('toast-container')
</div>
</body>

</html>

Now let's look at an example of the homepage:

home.blade.php
@extends(tt('layout.blade.php'))

@section('title')
{{ !empty(page()->title) ? page()->title : __('def.home') }}
@endsection

@push('content')
@navbar
<div class="container">
@navigation
@breadcrumb
@flash
@editor
</div>
@endpush

@if (tip_active('editor'))
@push('footer')
<script>
const IS_EDITING = {{ (int) page()->isEditMode() }};
</script>
@at(tt('assets/js/pages/home.js'))
@endpush
@endif
@footer

Let's break it down step by step.

In the main template, there's a @stack() serving as a "container" for collecting data from all templates.

@push() adds data to our "container." Simple, isn't it?

@navbar, @navigation, etc. - These are arbitrary functions added by the template itself. More details about this are described in the section on template development.

And at the top, there's the @extends which includes layout.blade.php wrapped in the tt() function.

warning

The tt() function returns the full path to the current template. For example, Themes/standard/.

In simple terms, @extends just calls the main template, which will already have content added to it. Simple as that. In modules, we do the same for creating our pages as we did for the homepage.

note

As a secret tip, you don't even need to do @extends() of the main template in module templates. You are not limited in any way. You can create your own layout or not use it at all. It's all in your hands.

Rendering Interfaces

To render an interface, all we need to do is render our template and return it as a Response inside the controller:

/** Assuming we have already created routes for this controller */
class ViewController
{
public function index()
{
// We simply return the render of our template as a Response
return view('Modules/Monitoring/Resources/Views/index');
}
}

More About Template Structure

Here's what functions, capabilities, and limitations templates have, described in the template development section.

Extending Standard Templates

If you want to extend a specific block globally in the template, you can do it very simply.

Just render your template on each page!

Wait, what?

Yes, you heard it right. To add a block to every page, you can globally render your template in the ServiceProvider:

template()->render('Modules/Monitoring/Resources/Views/test', [], false);

The template itself would have a structure like this:

test.blade.php
@push('container')
I'm added to the container, congratulate me!!!
@endpush

If you only want to insert data on a specific page (e.g., only on the homepage), you can do a check:

if( request()->is('/') ) { // Check if the current page is the homepage
template()->render('Modules/Monitoring/Resources/Views/test', [], false);
}