The Problem

Drupal lives on the server, but we need client-side context on the front-end in order to detect features and render pages properly in the ever-increasingly fragmented browserscape. It's already been suggested that we implement the client-side Modernizr builder within Drupal, but at the expense of standard caching methods that require anonymous traffic free of cookies. Additionally, this places responsibility on the end-developer or site administrator to properly assemble a Modernizr build.

Proposed Solution

Each module could declare HTML5 dependencies to Modernizr, which can then be translated into the appropriate feature test. Example: Geolocation Field would declare a Geolocation API dependency. I'm thinking hook_modernizr_api_alter() or similar. Themes can also register Modernizr API dependencies (for CSS3 and whatnot).

If asynchronous resource loading is desired, both modules and themes could use hook_modernizr_load_alter() to define Modernizr.load() calls. This scales better than .info definitions and paves the way for a more pluggable architecture down the road when both themes and modules will be needing to define complex front-end dependencies.

So now Modernizr knows what the Drupal installation needs to function properly, and the schema can be built during cron or cache clear, rather than on a per-request, cookie-driven basis. With the dependencies defined, we could pull from a full Modernizr library and produce a limited build consisting of only the components needed, very similar to how Modernizr Production builds work today. We could even feed this data to an admin UI, which could be manually tweaked if desired.

The end result is an automatically generated modernizr.custom.js that is as small and performant as possible, while providing all of the functionality needed within a specific Drupal implementation.

Roadmap

These issues track the development of this module's features:

These issues track the progress of other contrib modules as we add Modernizr integration to them:

CommentFileSizeAuthor
#3 rebuild-modernizr.png72.04 KBrupl

Comments

lewisnyman’s picture

I'm backing this. I started looking into this a couple of months ago. It's also worth noting that we can add our own additional tests using supporting modules without having to bloat up this module.

The production builder code is here:
https://github.com/Modernizr/site/tree/master/media/i/js

RobW’s picture

This is a fantastic idea.

rupl’s picture

StatusFileSize
new72.04 KB

I've updated the dev branch with hook_modernizr_info(). It allows any module to register tests, and provides an admin screen that links to the exact Modernizr production build that your site needs. Here's a sample from the module's own implementation:

function modernizr_modernizr_info() {
  $tests['cssclasses'] = array(
    'test' => 'cssclasses',
    'type' => 'Modernizr',
    'module' => 'Modernizr',
    'desc' => 'Utility - Allows Modernizr to inject CSS classes into <html>',
  );

  return $tests;
}

This hook ensures that the custom build includes the capability to inject classes into <html>. I added a couple other defaults as well (html5shim/IEPP, Modernizr.load).

To rebuild, visit admin/config/development/modernizr/rebuild. When you load the page, it lists the dependencies grouped by module, along with a link to the Modernizr download builder pre-populated with the correct settings. Just download and place in sites/all/libraries.

johnalbin’s picture

Issue tags: +frontend performance

Tagging for frontend performance.

RobW’s picture

I'm seeing three use cases for modernizer-Drupal integration:

1. A module utilizes an html5 feature (i.e., geolocation, local storage) and needs detection to polyfill functionality.
2. A theme uses modernizr classes to branch css along css3 feature detection.
3. A module is packaged with specific module display css and uses modernizr classes to branch css along css3 feature detection.

And two user groups:

A. Plug and play Drupal users who will need the module provided css.
B. Freelancers and firms who will be stripping out all css and developing from scratch.

Every combination of 1, 2, A, and B is a clear best-practice implementation. The third case is a little trickier. 3+A is all good. 3+B should have a way to selectively unset tests that are provided by 3 before modernizr build. Any thoughts?

rupl’s picture

@RobW, I agree that many of the cases are clear-cut. Hooray!

Regarding 3+B, I think the simple solution is to provide a drupal_alter() to complement the (yet to be created) hook_modernizr_load() (I had initially put my focus on calling Modernizr.load() from .info files, but I am leaning toward ripping this back out). Then a developer is free to change the tests and Modernizr.load() calls that other components have requested.

I agree that this is is where things could get tricky, as modules might require much more than cosmetic CSS3 to function properly. Geolocation is a prime example.

RobW’s picture

Right, modernizr detects css3/display features, and also html5/js functionality features, and I think that the API could benefit from making the distinction. Maybe a boolean that marks the modernizr test as "display" or "functional", so that developers can unset all "display" test registrations.

Then there's the case where a complex interface (e.g., Views UI) might require css3 properties to display correctly, in which case display would be functional and the useful distinction might be "theme layer/optional" and "functionality/required". Maybe a more useful distinction.

I'm also looking at this from my point of view, what would help me as a drupal and front end dev -- I'm not sure what the considerations are from a module/db level.

rupl’s picture

As mentioned in #1030822-8: Modernizr 2 custom builder (client-side for admin UI), the type attribute was repurposed. This allows tests, extras, groups, and other types of arguments to be supported in the drush custom builder command.

rupl’s picture

Title: Expose a Modernizr API to other Drupal modules » [Meta] Develop a Modernizr API for other Drupal modules

Changing title to reflect issue usage.

rupl’s picture

Issue summary: View changes

Updated issue summary.

rupl’s picture

Issue summary: View changes

Updated issues tracking API progress. Added section to track integration with other contrib modules.

rupl’s picture

Just bumping this to notify people that the two major issues supporting the API have been committed to dev! It is now possible to file issues against other modules asking for Modernizr 7.x-3.x support.

klonos’s picture

Great new Chris! Well done and thank you for spending time and effort on this ;)

PS: ...you're probably talking about #1278504: Call Modernizr.load() from theme .info files and #1661746: Create Modernizr.load() API

klonos’s picture

Issue summary: View changes

Update summary's roadmap.

rupl’s picture

Status: Active » Closed (fixed)

I just bumped the recommended version to be 7.x-3.x so I think this can be closed. Any issues with the API can be filed separately from now on. Hooray!

rupl’s picture

Issue summary: View changes

Updated issue summary. Added Geolocation integration issue.