9

According to the wiki page Adding Javascript and CSS to the Page, you can add a stylesheet with addStyleSheet like this:

$document = JFactory::getDocument();
$document->addStyleSheet($url);

Or with JHtml::stylesheet like this:

JHtml::stylesheet($url, array(), true);

But the wiki page Creating a Basic Template instructs the learner to include stylesheets like this:

<head>
    <jdoc:include type="head" />
    <link rel="stylesheet" href="<?php echo $this->baseurl ?>/templates/system/css/system.css">
</head>

This bypasses addStyleSheet and JHtml::stylesheet. Is this a good idea? When would you use the former and when would you use the latter?

Note: JHtml::_("script", …) and JHtml::_("stylesheet", …) are almost exactly the same as JHtml::script and JHtml::stylesheet. See What does JHtml::_ do.

1

5 Answers 5

7

JHtml is normally used in extensions as it's means overrides can be performed which is a really good feature if you're a developer. It also extends $document->... by adding some additional functionality.

Here is an example:

/js
   /script.js
   /script.min.js

When using JHtml, the minified version of the script will be loaded to reduce page loading times. When you enable debug mode in the Global Configuration, it will load the unminified version of the file to make it readable.

You cannot override a template in the same way you can for extensions, so a lot of templates use <link> because any overrides can simply be done by adding a custom.css file, then adding your code in it. Thus using the native <link> tags are faster then using the Joomla API to load the CSS file

7
  • So the only advantage of using JHtml for a template is to get minification?
    – Flimm
    May 22, 2015 at 10:26
  • @Flimm - Have a look here, where it will explain a little more in detail: docs.joomla.org/J3.x:Adding_JavaScript_and_CSS_to_the_page
    – Lodder
    May 22, 2015 at 10:33
  • That's the link in my question :) I just wanted clarification because it seemed weird that you would ever write the <link ...> code directyl.
    – Flimm
    May 22, 2015 at 10:48
  • 1
    In a template, it's perfectly fine to do this as you cannot override an actual template the way you can an extension, therefore importing an asset can be done without the Joomla API ;)
    – Lodder
    May 22, 2015 at 10:57
  • 1
    @Flimm JHtml also works with MD5SUM files, $document->addStyleSheet does not. magazine.joomla.org/issues/issue-nov-2014/item/… May 23, 2015 at 16:18
6

In Addition to the others, the single biggest benefit I have found is all CSS / JSS files are in the same array at 1 time.

This may not sound like a benefit, but a snippet from another example

<link rel="stylesheet" href="<?php echo $this->baseurl ?>/templates/system/css/system.css">

Later on when you want to change system.css, you will make changes and then realize that your users have the old system.css in their cache with your new content, meaning you will have to change the code to be a slightly different URL (or reduce your cache time and make the user download more often)

When you use the JHTML method when the template is generated you can then generate a "version" of the CSS / JS file (filemtime is a good one to use, or git commit ID etc) so changing the content instantly gives the new css to all people to view your site. Long cache times + instant re generation means less downloads per page.

Code sample (NOT TESTED WORKING, Though I do use similar code)

$styles  = $this['asset']->get('css');
if ($styles) {
  foreach ($styles as $style) {
    if ($url = $style->getUrl()) {
      if ($url[0] == "/") {
      //its local, find it and add the mtime
        if (file_exists(getcwd() . $url)) {
          $url .= "?" .filemtime(getcwd() . $url);
        }
      }
      printf("<link rel=\"stylesheet\" href=\"%s\" type=\"text/css\" />\n", $url);
    } else {
      printf("<style>%s</style>\n", $style->getContent());
    }
  }
}

This code will need tweaking for your system to make sure the paths are found correctly

0
5

Joomla provides its own API from their Factory we can call it as JFactory.

There is no harm of using:

<link rel="stylesheet" href="<?php echo $this->baseurl ?>/templates/system/css/system.css">

over:

$document = JFactory::getDocument();
$document->addStyleSheet($url);

However, if you are including your stylesheets with above method, then it will be included in <head> section of your template automatically with <jdoc:include type="head" />. Going further, if we are developing our own extension and if you are explicitly want to have your own CSS or Javascript then you can declare it with above method. It will again add it in your <head> section and avoiding you to update your template's index.php

Sometimes you want your scripts to be appear at the end of your body to get all DOM elements loaded. At this situation you may want to include your scripts at the end of your <body> element with following:

<script type="text/javascript" src="myScript.js"></script>

You will also get additional control for handling CSS and scripts for e.g. you can unset scripts and stylesheets programmatically if not needed.

2
  • I understand that JFactory puts the stylesheet in <jdoc:include type="head" />, my questions is why bother using it in a template when you can just write the <link ...> line yourself?
    – Flimm
    May 22, 2015 at 10:29
  • It is perfectly fine to use <link...> in template. But every framework/CMS has it's own implementation way. Joomla is no exception. It's a Joomla way to render scripts and stylesheets. As far as there is no way to override template, we can still rely on old <link...> markup. May 22, 2015 at 11:30
0

There are a couple of additional benefits for using the "addXxxxx" methods for loading stylesheets and javascripts.

There are extensions you can install that will put those files together and gzip them into a single file, thus improving page speed (by reducing http requests and the file sizes).

Also, you can use them in template and layout overrides to ensure required files get loaded. For example, if a few of your content items require a specific javascript library (such as a library to do Masonary-style dispalys of photographs) you can create a specific layout for those types of articles which will use that mechanism to load the js library and style sheets specific for those kinds of displays. This means that extra weight only gets added to the pages that need it, but still keeps the version information in one place, so one edit will change multiple page displays, rather than having to make multiple changes when things change (and we all know they will change).

Personally, I consider those advantages, plus the ability to override those files with different copies when required, to be enough to make that my preferred way of adding them.

-1

if you use <link > your joomla head will not be tidy because the <link > will show under javascript block, outsite <jdoc:include type="head" /> and joomla will back to folder css again. This will affect the performance of joomla is supposed to. And if you use <link > you will get many variable echo in plain index.php :(

I use $doc->addStyleSheet because the .css will be show on css block ,inside <jdoc:include type="head" />. that same for javascript use $doc->addScript. After <jdoc:include type="head" /> joomla will assume all finished and will do more important work. :)

Some people use <link > for unsupport browser like ie

<!--[if IE 8]>
<link href="<?php echo $this->baseurl ?>/templates/<?php echo $this->template; ?>/css/ie8only.css" rel="stylesheet" type="text/css" />
<![endif]-->

<!--[if lt IE 9]>
    <script src="<?php echo $this->baseurl ?>/media/jui/js/html5.js"></script>
<![endif]-->

it will be show on the bottom of <jdoc:include type="head" />.

3
  • This doesn't actually answer the question that has been asked. If you believe the code you've provided is the best method, explain why.
    – Lodder
    May 28, 2015 at 23:57
  • You say that <link> tag will appear after <jdoc:include type="head" />, but this only happens if you add the code after it. If you add it before, it will appear before. In regards to echoing PHP variables in the index.php, I have no idea what you mean when you say this. Using <link> tags is basic HTML and Joomla doesn't change the way this works
    – Lodder
    May 29, 2015 at 14:56
  • and you will add before <jdoc:include type="head" /> ? @Lodder May 29, 2015 at 15:00

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.