ResourceLoader/Writing a MobileFrontend friendly ResourceLoader module

From MediaWiki.org
Jump to: navigation, search
shortcut: RL/M

This document provides guidance on developing ResourceLoader modules to run in mobile site as provided by the MobileFrontend extension.

About MobileFrontend Extension[edit]

The MobileFrontend extension by default specifically disables all ResourceLoader modules. This is for good many reasons:

  1. Many modules were not designed nor tested to run on mobile
  2. On mobile the screen resolution can vary greatly - many beautifully designed modules will not function on mobile
  3. Many features available on desktop are not available on mobile
  4. Reducing payload - many mobile users are on slow internet connections - adding modules to the mobile experience can reduce this drastically.
  5. The mobile CSS/JavaScript landscape is very different from desktop. e.g. position:fixed support

Styling for mobile[edit]

By default you should style for mobile and use the following rules:

  • Restrict your design to a 320px screen, maybe simplifying the user interface where needed.
  • Use % widths and em's - avoid using pixels as much as possible!
  • If you need to use px's make sure they are no bigger than 50px.
  • Use media queries to style for desktop. Adapt your design when the minimum width of the screen is 768px. This will make your design look good on mobile, tablet and desktop screens.
/* deviceWidthTablet is a global LESS variable which defines the threshold when to invoke tablet styles */
@media all and (min-width: @deviceWidthTablet) {
  • Note that media queries are not supported in IE6,7,8. Either don't worry about this or use a JavaScript shim to pull in those styles for those browsers.

Why does mobile turn my ResourceLoader modules off by default?[edit]

Note good web practice states that you should have good fallbacks for non-JavaScript users. There are variety of reasons why you should care about non-JavaScript experiences and if the crucial functionality of your feature is not working on mobile, it's probably time to go back to basics and make sure it does.

There is a good reason why that we decided to turn ResourceLoader modules off by default. "We want you to think about mobile."

By breaking your toy, we force you to make a decision. Namely that decision is 1) Do I do the bare minimum to get it working 2) Do I rethink my feature for mobile 3) Do I support only desktop mode (and make that obvious to the user) or 4) Do I leave my feature broken.

Provided your answer is not 4, your answer is acceptable :-)

We broke `your toy` because:

  • By breaking your feature it forces you to think about mobile experiences. If you've noticed it is broken, you care and can think about it. Making breakage less obvious could have the adverse effect of your feature staying broken (given it is relatively trivial in most cases to get it work).
  • Some modules may not have been built with mobile in mind and could cause a mobile browser to crash due to heavy CPU usage. e.g. a maps based application.
  • An interface built ten years ago may have been built with desktop devices in mind, and may require a desktop experience e.g. it might optimise for viewing with a resolution of at least 600px
  • Sometimes a completely different experience is warranted. Using targets you can decide to give a completely different experience to your mobile site users. For instance a photo curation tool might work better on mobile devices if it has a swipe left/swipe right interface rather than a table experience on desktop.
  • Certain key interface elements may not be easily clickable on mobile - for instance a list of search results which is less than 40px (Haven't been designed for the fat finger)
  • Making a site mobile friendly is not necessarily a case of slapping some media queries on to it - another approach would be to make your site mobile first and rethink your feature altogether.
  • In mobile we care a lot about resources loaded. We are trying our darn hardest to shrink the size of assets down as far as possible to give our users in countries with slower connections the best possible experiences. As a result we only allow standard JavaScript libraries and standard styles for interface elements as decided by the ux standardisation project.
    • If your module uses jquery.ui - it's time to rewrite it. On mobile it would be irresponsible to load jquery.ui and oojs.ui when both libraries solve similar problems.
    • We don't load common scripts or MediaWiki:Common.js/css as these were designed without mobile in mind - many of the rules are not useful for mobile screens and greatly increase the payload. We were also not keen for existing users to have the mobile site explode in front of their faces due to assumptions made by these scripts e.g. I am on Vector and this DOM element is available.

Making your modules mobile friendly[edit]

Decide if you should[edit]

Just because you can you must decide whether this is worthwhile.

  • Will people on mobile really use your module?
  • It is useful to slow down the mobile experience by providing this module?
  • IS there some other library already enabled for mobile that does this thing already. For instance if you are styling a button, why not use the mediawiki.ui.button library in core?

If you are not sure it is suggested that you start a conversation on the mobile-l mailing list and also gather feedback from the communities that will use your module.

If your module comes with a large amount of client side code it is a good indication that your module probably needs rethinking or not applying to mobile. Compare your module to the jQuery library - if it is bigger than that or even near to its size you are probably doing the wrong thing.

An alternative approach may be to present a message in your display saying "This tool only works on desktop. Please switch to desktop view to use this."

Decide when to add the module[edit]

Are you adding the module under the right circumstances? For instance if your module enhances the editing experience - make sure you only add that module when the user is on an edit page. You should be extremely careful about adding modules to pages as each module comes with a download penalty.

Enabling your existing modules[edit]

First things first make a clone of the module you want to enable on mobile. In the cloned module define the targets property. Set it to mobile. This ensures your module can run in mobile.

Here is an example used to enable CentralNotice for mobile.

$wgResourceModules['ext.centralNotice.bannerController'] = array(
	'localBasePath' => $dir . '/modules',
	'remoteExtPath' => 'CentralNotice/modules',
	'scripts'       => 'ext.centralNotice.bannerController/bannerController.js',
	'position'      => 'top',
	'dependencies'  => array(
		'jquery.cookie',
	),
);

$wgResourceModules['ext.centralNotice.bannerController.mobile'] = $wgResourceModules['ext.centralNotice.bannerController'] + array(
	'targets' => 'mobile',
);

You now need to add this new module to the mobile output page. To do this make use of the MobileSiteOutputPageBeforeExec hook. Note the $mode parameter allows you to target your modules at the 'beta' or 'alpha' versions of the site. This is a great way to test your module out in the wild to a smaller audience. The 'alpha' version is a great way to test a module that you are not sure you have got right and get feedback from various users.

function efEnableMobileModules( $out, $mode ) {
	$name = 'ext.centralNotice.bannerController.mobile';
	if ( $mode !== 'stable' ) {
		$out->addModules( $name );
	}
	return true;
}

Moving your module to stable[edit]

To do this simply add the module unconditionally.

function efEnableMobileModules( $out, $mode ) {
	$name = 'ext.centralNotice.bannerController.mobile';
	$out->addModules( $name );
	return true;
}

Testing your modules[edit]

  • At minimum you should test on the following browsers:
    • iPhone
    • Android 2.x
    • Android 4.x
    • Opera Mini v7+
    • Blackberry v6+
  • The MediaWiki JavaScript API is currently much smaller than the desktop API. Ensure that your modules do not use anything that is not available.
  • Many MediaWiki-based projects should work on as many devices as possible.
  • Some things to test in the styles themselves?
    • Do floats only get enabled on tablet and higher? e.g. via a media query. Floats rarely work on mobile screens and will need to be scoped to tablet and desktop.
    • Are any widths fixed? How will these degrade on a mobile resolution? Fixed widths in general should be avoided, but where necessary they should be scoped to tablet and desktop via a media query.
    • Are any font sizes fixed? How will these change as the user zooms in and out of the mobile device? Font sizes generally should be defined in terms of em, rem and %.

Targeting mobile devices[edit]

The mobile skin on Wikimedia servers runs on the Minerva skin, however it's worth noting you can also get the Vector skin in mobile and the Minerva skin in desktop. It's thus not helpful to have the mindset "I only want to run this code on mobile".

When targeting mobile devices think about features available, e.g. DOM elements on the page OR think in terms of how the browsers available viewport. How does your feature work at 320px? How does it work at 720px? What happens if the DOM element #caEdit is not present on the page?

As a last resort you can also use:

if ( mw.config.get( 'skin' ) === 'minerva' )

but this should only be used in circumstances where you want to blacklist the skin to avoid support.

Experimenting with mobile[edit]

You can experiment with mobile by making use of a user script/style in your username space:

User:YourName/minerva.css, User:YourName/minerva.js

Note that if you want to run code on all mobile skins (e.g. also on Vector skin in mobile ) use:

User:YourName/mobile.css and User:YourName/mobile.js


ResourceLoaderResourceLoader
Documentation FeaturesResourceLoader/Features · VocabularyResourceLoader/Vocabulary · Migration guide (users)ResourceLoader/Migration guide (users) · Migration guide (developers)ResourceLoader/Migration guide for extension developers · Developing with ResourceLoaderResourceLoader/Developing with ResourceLoader · Core modulesResourceLoader/Modules · Mobile supportResourceLoader/Writing a MobileFrontend friendly ResourceLoader module
Project information Status updatesResourceLoader/status · Version 1 Design SpecificationResourceLoader/Version 1 Design Specification · Version 2 Design SpecificationResourceLoader/Version 2 Design Specification · RequirementsResourceLoader/Requirements
Other JavaScript DeprecationsResourceLoader/Legacy JavaScript