1.0 ¿Qué aprenderemos?
- A crear un proyecto
- A definir rutas
- A usar plantillas
- A incluir plantillas dentro de otras
- A conocer el
path
de las rutas en twig - A conocer la ruta actual en twig
- A usar el operador ternario y el operador
or
en twig
1.1 Crear un proyecto
1
composer create-project symfony/website-skeleton symfony-blog
- Descargar la plantilla de la web
- Se descomprime en
public
- Comprueba que la web funciona
1.2 Definir las rutas
Vamos a crear las rutas para cada una de las páginas.
El primer paso es crear un Controlador
1
php bin/console make:controller PageController
Este controlador va a encargarse de la página de portada
y de la página about
.
1.2.1 Ruta /
El código que se genera automáticamente es el siguiente:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
<?php
namespace App\Controller;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\Routing\Annotation\Route;
class PageController extends AbstractController
{
#[Route('/page', name: 'app_page')]
public function index(): Response
{
return $this->render('page/index.html.twig', [
'controller_name' => 'PageController',
]);
}
}
Ahora eliminamos la página que genera automáticamente en templates/page/index.html.twig
, movemos la página public/index.html
a templates/page/index.html.twig
y modificamos el controlador para que quede así:
1
2
3
4
5
#[Route('/', name: 'index')]
public function index(): Response
{
return $this->render('page/index.html.twig', []);
}
Hemos creado la ruta /
y la hemos nombrado como index
Ya podemos probar la página de portada http://127.0.0.1:8080/
1.2.1.1 Plantilla base
Todas las páginas comparten la cabecera y el pie de página, así que vamos a crear la plantilla base.html.twig
.
-
Copia el contenido de
index.html.twig
dentro debase.html.twig
-
Ahora
index.html
va a extender la plantillabase
1
{% extends 'base.html.twig' %}
-
Comprueba que sigue funcionado la portada
-
En la plantilla
base.html.twig
vamos a crear dos bloques:-
Uno para el título que va a variar en cada página: Localiza la etiqueta
title
y modifícala así:1
<title>{% block title %}Inicio{% endblock %}</title>
-
Otro para el cuerpo de la página: Localiza el código entre
1
<div id="index">
y
1
</div><!-- End of index box -->
cópialo y sustitúyelo por:
1
{% block body %}{% endblock %}
Este es el código que va a variar entre página y página. El código cortado vamos a pegarlo en la página
index.html.twig
dentro del bloquebody
1 2 3
{% block body %} //Código cortado de base.html.twig {% endblock %}
Ya solo nos queda modificar el título de la página
/
.1
{% block title %}Index{% endblock %}
-
-
Comprueba que la página sigue funcionado
1.2.2 Ruta /about
Creamos el controlador
1
2
3
4
5
#[Route('/about', name: 'about')]
public function about(): Response
{
return $this->render('page/about.html.twig', []);
}
Movemos la página about.html
a /templates/page/about.html.twig
1
2
3
4
5
6
7
{% extends 'base.html.twig' %}
{% block title%}About{% endblock %}
{% block body%}
<!-- Principal Content Start-->
//Código html de about
<!-- End of principal content -->
{% endblock %}
Comprueba que funciona la ruta /about
1.2.3 Reto - Rutas /contact
, /blog
y /single_post
Crea las rutas
/contact
enPageController
, y las rutas/blog
y/single_post
enBlogController
Ten en cuenta que en
blog.html
existen enlaces asingle_post.html
que deberás cambiar para llamar a la rutasingle_post
1.3 Menú de navegación
Como habéis podido comprobar, el menú de navegación ha dejado de funcionar ya que apunta a las páginas .html
Vamos a crear una partial
para la navegación.
-
Identificamos el código de
base.html.twig
que pinta la navegación y lo movemos atemplates/partials/_navigation.html.twig
. Por convención, los partials empiezan por_
-
Modificamos
base.html.twig
para que incluya este partial1
{{ include ('partials/_navigation.html.twig')}}
-
Ya podemos modificar el partial para que apunte a las nuevas rutas. Hemos de usar la función de twig
path
que nos devuelve el path a una ruta con nombre. Nuncaharcodéis
las rutas que para eso se les asigna un nombre en el controlador. Ten en cuenta que la dirección de la ruta podría cambiar durante el desarrollo del proyecto pero el nombre no debería hacerlo.1 2 3 4 5 6 7 8 9 10 11 12 13 14
<ul class="nav navbar-nav"> <li class="active lien"><a href="{{ path('index') }}"> <i class="fa fa-home sr-icons"></i> Home</a> </li> <li class=" lien"><a href="{{ path('about') }}"> <i class="fa fa-bookmark sr-icons"></i> About</a> </li> <li class=" lien"><a href="{{ path('blog') }}"> <i class="fa fa-file-text sr-icons"></i> Blog</a> </li> <li><a href="{{ path('contact') }}"> <i class="fa fa-phone-square sr-icons"></i> Contact</a> </li> </ul>
Pero ahora lo que ocurre es que siempre está seleccionada la opción de menú
home
porque es la que tiene la clase cssactive
.
Vamos a arreglarlo. Para ello hemos de conocer cuál es la ruta activa y añadir la clase active
a dicha ruta. Por suerte, existe la función twig
app.request.attributes.get('_route')
que nos devuelve dicha ruta.
Por ejemplo, en el caso del enlace a index
quedará así:
1
2
<li class="{{ (app.request.attributes.get('_route') == 'index') ? 'active': ''}} lien">
<a href="{{ path('index') }}"><i class="fa fa-home sr-icons"></i> Home</a></li>
Estamos usando el operador ternario (condition ? result when true : result when false)
1
{{ (app.request.attributes.get('_route') == 'index') ? 'active': ''}}
1.3.1 Reto
Modifica la navegación para cada una de las rutas. Ten en cuenta que el menú
blog
se debe activar para las rutasblog
ysingle_post
Nota En twig se puede utilizar el operador
or