.. include:: /Includes.rst.txt .. _basic-concepts: Basic Concepts ============== Fluid is a template engine which lets you display content on a website very easily. A specific file (the template) will be processed and the containing placeholders will be replaced with the current content. This is the basic concept of template engines - as well as Fluid's. Fluid is based on three conceptual pillars which build the backbone of the template engine and provide for scalability and flexibility: * *Object Accessors* output the content of variables which were assigned to the View to be displayed. * *ViewHelpers* are special tags in the template which provide more complex functionality such as loops or generating links. * *Arrays* make it possible to assign hierarchical values to ViewHelpers. Outputting Data with Object Accessors ------------------------------------- A template engine uses a placeholder to fill content in specified areas in a template and the result is then returned to the user. In Fluid, these placeholders are called *Object Accessors*. .. tip:: The markers used in the classic marker based templates of TYPO3 v4 are also placeholders which are replaced later on by the desired data. You will notice though, that the placeholders used in Fluid are clearly more flexible and versatile. Object Accessors are written in curly brackets. For example, `{blogTitle}` will output the content of the variable `blogTitle`. The variables have to be assigned in the controller with :php:`$this->view->assign(variableName, object)`. Let us look at this in an example of a list of blog posts. In the controller, we assign some data to the template with the following code:: namespace ExtbaseTeam\BlogExample\Controller; class PostController extends \TYPO3\CMS\Extbase\Mvc\Controller\ActionController { // ... public function indexAction(\ExtbaseTeam\BlogExample\Domain\Model\Blog $blog) { $this->view->assign('blogTitle', 'Webdesign-Blog'); $this->view->assign('blogPosts', $blog->getPosts()); } } Now we can insert the string »Webdesign-Blog« into the template with the Object Accessor ``{blogTitle}``. Let us take a look at the associated template::

{blogTitle}

{post.title}
Upon generation of the output, the Object Accessor ``{blogTitle}`` will be replaced by the title of the blog »Webdesign-Blog«. To output the individual blog posts, the tag ```` is used, which you can also see in the template above. Depending on the title of each blog post, the complete output looks like this::

Webdesign-Blog

Fluid as template-engine
TypoScript to configure TYPO3
.. tip:: If you want to output an object instead of a String, the object needs to have a ``__toString()``-method which returns the textual representation of the object. In the example above, you will also find the Object Accessor ``{post.title}`` which is used to output the title of a blog post. This hierarchical notation is a syntax that makes it possible to walk through associations in the object graph - you can literally move from object to object. Often, a complex object is assigned to the View, but only parts of it will be displayed. In the example above, we used ``{post.title}`` to display the property ``title`` of the object. Generally, Fluid tries to handle such hierarchical properties in the following order: * If ``post`` is an array or an object which implements the interface ArrayAccess, the corresponding property will be returned as long as it exists. * If it is an object, and a method `getTitle()` exists, the method will be called. This is the most common use case of an Object Accessor, since by convention all public properties have a corresponding ``get``-method. * The property will be returned if it exists in the object and it is public. We discourage the ability to utilize this though, since it violates the Uniform Access Principle (see box) .. sidebar:: The Uniform Access Principle The Uniform Access Principle says, all services offered by a module should be available through an uniform notation which does not betray whether they are implemented through storage or through computation. Explanation on Wiki Stored objects are being accessed directly using public class variables in PHP - and it is visible on the outside that the object isn't being computed. For this reason, we often use get and set-methods in our models. Therefore, all options of the class are accessible through method calls and are uniformly addressed - it is not visible on the outside whether the class computed or stored the value directly. You can navigate through more complex objects, because Object Accessors can be nested multiple times. For example, to output the email address of an author of a blog post, you can use ``{post.author.emailAddress}``. That's almost equivalent to the expression ``$post->getAuthor()->getEmailAddress()`` in PHP, but focused on the essential. Only the get-method, and not just any method, of an object can be called with Object Accessors. This ensures that there is no PHP code in the template. It is better to place PHP code in your own ViewHelper if needed. The following describes how to do this. Implementing more complex functionalities with ViewHelpers ---------------------------------------------------------- Functionalities that exceed the simple output of values have to be implemented with ViewHelpers. Every ViewHelper has its own PHP class. Now, we're going to see how we can use ViewHelpers. Later, you'll also learn how to write your own ViewHelper. To use an existing ViewHelper, you have to import the *Namespace* and assign a shortcut to it. You can do this with the declaration ``{namespace ...=...}``. All Namespaces used in your template must always be registered. This might seem redundant, but because all important information is embedded in the template, readability increases immensely for other template editors who work on the same templates. The standard ViewHelper of Fluid will be imported and assigned to the shortcut ``f`` with the following declaration:: {namespace f=TYPO3\CMS\Fluid\ViewHelpers} This Namespace will be imported automatically by Fluid. All ViewHelpers that come with Fluid are prefixed with ``f``. Your own Namespaces have to be imported into the template like previously mentioned. All tags, which begin with a registered prefix, will be evaluated. Here's a small example: .. code-block:: xml Tags without a registered prefix (in this example