Font Awesome 6 Official WordPress Package
This guide is for developers seeking to use wordpress-fontawesome
as a package
in a WordPress plugin or theme.
WordPress users should consult the plugin's description in the WordPress plugin directory for guidance on using Font Awesome in WordPress.
- wordpress-fontawesome
- Contents
- Description
- Why Use a Package?
- Adding as a Composer Package
- Installing as a Separate Plugin
- API References
- Usage in Pages, Posts, and Templates
- Usage in Gutenberg (Blocks)
- Detecting Configured Features
- What Gets Enqueued
- Loading Efficiency and Subsetting
- How to Make Pro Icons Available in Your Icon Chooser
- Query the Font Awesome GraphQL API
- Examples
- Contributing Development to this Package
This package adds to your plugin or theme the following abilities:
- use Font Awesome SVG, Web Font, Free or Pro, with version 4 compatibility, loading from the Font Awesome CDN.
- use Font Awesome Kits
- an
[icon]
shortcode - detection and resolution of Font Awesome version conflicts introduced by other themes or plugins
- coordination of configuration preferences by any number of plugins or theme that may be using this package on the same WordPress site.
- management of Font Awesome account authorization via API Token
- management of Font Awesome releases metadata (available versions and related metadata)
- Font Awesome GraphQL API queries authorized by the site owner's API Token
If you're a WordPress developer, then you already know how to use wp_enqueue_style
or wp_enqueue_script
to load assets like Font Awesome. So why take a dependency
on another package to do that for you?
Because Font Awesome is so popular among themes and plugins, and because it's so easy for a developer to enqueue the Font Awesome assets, it's become a jungle out there for our users.
Some WordPress site owners have been known to have a theme and three different plugins installed, each trying to load its own self-hosted version of Font Awesome:
- mixing version 4 or 5 with version 6
- mixing SVG with Web Font
- sometimes even Font Awesome version 3
This package provides sophisticated conflict detection, resolution, and error reporting, empowering our users to solve their compatibility problems quickly.
Also, back when many themes and plugins began including Font Awesome, there was no Pro version. Now there is, and there's a constant stream of new icons, styles, and features being added.
Font Awesome Pro subscribers should be able to use their Pro goodies in your theme or plugin. But since Font Awesome's licensing doesn't allow you to distribute Font Awesome Pro, you'd have to rely on the user to do some kind of setup on their end to enable it. Why reinvent that wheel?
And even if you do, you'd still have those compatibility problems with other themes and plugins, which you may be making even worse by giving the user yet another way to add another conflicting version of Font Awesome to their WordPress site.
Some WordPress developers have solvd the Pro problem by not shipping the Font Awesome assets, but shipping the Pro metadata to drive their icon choosers. That locks you into whatever version of Font Awesome Pro you happened snapshot when you release. But again, there's a constant flow of new icons and features being added to Font Awesome Pro. Font Awesome Pro subscribers love having access to those new icons when they come out, so let's help them stay current.
This package allows the user to manage the version of Font Awesome, while giving you, the developer, runtime access to all metadata for whatever version the user chooses.
Power-up those icon choosers with integrated Algolia search--the same icon search that powers the Icon Gallery on fontawesome.com. With 7,000+ icons and growing, search makes finding the right icon--by name, category, or conceptual similarity--much easier for users. Why re-invent that wheel?
We can't say much right now, but there some big stuff coming to Font Awesome Pro that will only be accessible through an authenticated Font Awesome account.
You could manage everything related to authorizing Font Awesome accounts to access those features (which your users are definitely going to want to use on their WordPress sites!) But again, why re-invent that wheel?
composer require fortawesome/wordpress-fontawesome
In your code, requiring this package's index.php
will cause the version of
the package as bundled by your theme or plugin to be added to the list of
possible versions to be loaded by the FontAwesome_Loader
. The loader coordinates
among potentially multiple installations of the plugin, ensuring that the latest available
version of the package is loaded and used at run time.
require_once __DIR__ . '/vendor/fortawesome/wordpress-fontawesome/index.php';
# optional, for conveniece
use function FortAwesome\fa;
You should register your code as a client of Font Awesome, even if you have no configuration preferences to specify, because the Font Awesome Troubleshoot tab will show the WP admin a listing of which plugins or themes are actively using Font Awesome, what their preferences are, and what conflicts there may be.
Do not register any preferences if you don't really need to. It will be a better experience for the WP admin user if your theme or plugin can adapt to their changes of Font Awesome preferences without complaint from your code.
See the API documentation for the preferences schema.
add_action(
'font_awesome_preferences',
function() {
fa()->register(
array(
'name' => 'plugin foo'
// other preferences would be registered here
)
);
}
);
There are basic principles for initialization and cleanup that apply in either case, but the implementation details will vary depending on whether you're building a theme or a plugin.
When your theme or plugin is activated, it should invoke FortAwesome\FontAwesome_Loader::initialize
.
This will ensure that Font Awesome is initialized without interfering with any
existing Font Awesome configuration that may already be present from some other theme's
or plugin's use of this package. In other words initialize()
can be called multiple times,
but subsequent invocations will not overwrite or reset prior saved settings.
Plugin Activation
Your plugin code should do something like this:
register_activation_hook(
__FILE__,
'FortAwesome\FontAwesome_Loader::initialize'
);
Theme Activation
Your theme code should do something like this:
add_action('after_switch_theme', 'FortAwesome\FontAwesome_Loader::initialize');
When your theme or plugin is deactivated,
it should invoke FortAwesome\FontAwesome_Loader::maybe_deactivate
.
This will ensure that the Font Awesome deactivation logic is run if your theme or plugin is the last known client of Font Awesome. Otherwise, the state of the database is left alone, for the sake of any remaining Font Awesome clients.
Plugins have a specific deactivation hook that is separate from an uninstall hook. There are different things to clean up in each case.
Themes don't have the same lifecyle hooks as plugins. In your theme, you might want to handle deactivation and uninstallation differently than the examples below, but these will get the job done.
Plugin Deactivation
Your plugin code should do something like this:
register_deactivation_hook(
__FILE__,
'FortAwesome\FontAwesome_Loader::maybe_deactivate'
);
Theme Deactivation
A theme is deactivated when some other theme is activated instead. At that time,
the switch_theme
action is fired. This is an opportunity for your theme to run
both the deactivation and uninstallation logic.
Both should probably be run from that one callback, since there's no separate, subsequent uninstall
hook for themes as there is for plugins.
(NOTE: if you're a theme developer who knows a better pattern for us to use here, please open an issue on this repo with a suggestion.)
add_action('switch_theme', function() {
FortAwesome\FontAwesome_Loader::maybe_deactivate();
FortAwesome\FontAwesome_Loader::maybe_uninstall();
});
When your theme or plugin is uninstalled, it
should invoke FortAwesome\FontAwesome_Loader::maybe_uninstall
.
Similarly, this will ensure that the Font Awesome uninstall logic is run if your theme or plugin is the last known client of Font Awesome. Otherwise, the state of the database is left alone, for the sake of other themes or plugins.
Plugin Uninstall
Your code should do something like this:
register_uninstall_hook(
__FILE__,
'FortAwesome\FontAwesome_Loader::maybe_uninstall'
);
Theme Uninstall
There's no hook for themes that's analogous to the register_uninstall_hook
for plugins.
For themes, our last chance to run uninstall logic is on the switch_theme
action hook,
as noted above under Theme Deactivation.
This package is also available as a plugin in the WordPress plugin directory.
You could instruct your users to install that plugin separately. Once activated, using the PHP API works the same as if you had included this package via composer.
Here are some relevant APIs:
- PHP API: any theme or plugin developer probably needs this
- GraphQL API: you may need this if you write code to query for metadata about icons, such as when building an icon chooser
- JavaScript API: you may need this if you are working directly with the JavaScript objects, such as when for doing some custom SVG rendering in Gutenberg blocks
- react-fontawesome component: you might prefer this instead of doing low-level JS/SVG rendering
Your templates can use standard <i>
tags in the all the ways described in the
Font Awesome quick start.
If Font Awesome is configured to use SVG technology, you can also use all of the SVG-only features, like Power Transforms.
[icon name="stroopwafel" prefix="fal"]
The name
attribute is just the name of the icon, not the CSS class name.
The prefix
attribute defaults to fas
, but must be specified for other styles.
Many themes and plugins use CSS Pseudo-elements to do things like adding icons
:before
the <li>
elements in menus.
This was a common practice for users of Font Awesome 4 and earlier and tends to
work fine as long as the font-family
in your CSS rules is known and never changes,
and as long as the Font Awesome technology is always CSS with Web Font, and not
SVG.
You should not make any of those assumptions. It's one of the most causes of "my icons are broken" when WordPress users attempt to change the version of Font Awesome loaded on their site.
Font Awesome 5 & 6 do not use the same font-family
as Font Awesome 4 did.
It uses multiple different font-family
values that vary by icon style.
Also, while pseudo-elements perform nicely with CSS and Web Font technology, getting them to work with the SVG technology requires a lot of extra processing that can cause significant performance problems in the browser. It's really only provided as an accommodation when pseudo-elements can't be avoided. This is why pseudo-elements are not enabled by default when configured for SVG technology.
Your plugin can register a preference for Web Font technology or pseudo-elements, if you must. But the WordPress site owner ultimately determines the configuration of Font Awesome. They may have to negotiate the requirements of multiple plugins or themes, some of which may not be playing nice. It can be a difficult balancing act.
Ease their pain by using a flexible and maximally compatible approach in your code.
Simply using <i>
tags or [icon]
shortcodes avoids the potential compatibility
or performance problems that come with pseudo-elements.
There are several ways one might incorporate Font Awesome icons in Gutenberg development.
Here are some considerations for you as you determine your approach:
The default configuration of the SVG with JavaScript technology that is loaded by this
package, whether via CDN or Kit, is autoReplaceSvg: true
. This means that:
- When the DOM loads, any
<i>
tags that look like Font Awesome icons are replaced with their correspoding<svg>
elements. - Any time the DOM is mutated to insert an
<i>
element dynamically, that<i>
element is also replaced with its corresponding<svg>
.
So, if your Gutenberg code renders icons as <i>
tags, and the active Font Awesome
technology is SVG, then your rendered <i>
tags will be immediately replaced
with <svg>
elements. That may or may not be what you want.
If the autoReplaceSvg
behavior is not what you want, you should not disable it
if there's any chance that other themes, plugins or content creators may be relying
on it. Instead, consider one of the alternatives to <i>
tags below.
The WordPress admin may have enabled Web Font technology instead of SVG.
This is not necessarily a problem, as long as your Gutenberg code is only rendering
icons <i>
elements anyway, and you're not using any SVG-only features like
Power Transforms, or Text, Layers, or Counters.
It just means that your rendred <i>
elements will remain <i>
elements in the
DOM and not replaced by <svg>
elements.
The Web Font technology does not
replace the <i>
elements, it matches their CSS classes with the appropriate
glyph lookups in the associated web fonts loaded by the Font Awesome CSS.
This point can be inferred from the previous two. If your Gutenberg code works
by rendering <i>
elements, it would be best to ensure that it works equally
well when Font Awesome is configured either for SVG or Web Font.
You could make it an error to run your code with Font Awesome technology as Web Font. If you know that your code absolutely must have the SVG with JavaScript technology to work properly, you could detect the presence of that feature and have your code respond accordingly.
In the WordPress server PHP code, you can call fa()->technology()
and expect
it to return "svg"
.
In the browser, the Font Awesome JavaScript API will be present on the global FontAwesome
object only when SVG with JavaScript is loaded.
You should also register a preference for SVG in your font_awesome_preferences
action hook:
add_action(
'font_awesome_preferences',
function() {
fa()->register(
array(
'name' => 'plugin foo',
'technology' => 'svg'
)
);
}
);
This approach comes at the cost of limiting compatibility, though. It either limits when your code can run, or it creates a potential mutual exclusion with other themes or plugins that work better with Web Font technology.
Generally, our goal is to maximize compatibility and thus minimize pain for the WordPress user.
If all.js
is loaded, and it is when fa()->technology() === "svg"
and
fa()->using_kit()
is false
, then the IconDefinition
objects for all icons
in the installed version of Font Awesome may be looked up
with findIconDefinition()
.
If fa()->pro()
is also true
then the fal
style prefix will also be available.
So the following
would get the IconDefinition
object for the coffee
icon in the Light style.
const faLightCoffee = FontAwesome.findIconDefinition({ prefix: 'fal', iconName: 'coffee' })
The faLightCoffee
object can then be used with icon()
, for example, to get
an html rendering of the icon as an <svg>
element:
FontAwesome.icon(faLightCoffee).html
would produce something like:
[
'<svg data-prefix="fal" data-icon="coffee" class="svg-inline--fa fa-coffee fa-w-18" ...>...</svg>
]
This html could be stored directly as page content.
Or an abstract object could be generated that you could use to create your own DOM elements or store in the attributes of your Block:
FontAwesome.icon(faLightCoffee).abstract
would produce something like:
[
{
"tag": "svg",
"attributes": {
"aria-hidden": "true",
"focusable": "false",
"data-prefix": "fal",
"data-icon": "coffee",
"class": "svg-inline--fa fa-coffee fa-w-18",
"role": "img",
"xmlns": "http://www.w3.org/2000/svg",
"viewBox": "0 0 512 512"
},
"children": [
{
"tag": "path",
"attributes": {
"fill": "currentColor",
"d": "M517.9...64z"
}
}
]
}
]
react-fontawesome
is another alternative to <i>
tags.
When you already have an IconDefinition
object, it's easy:
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome'
// ...
const lightCoffeeComponent = <FontAwesomeIcon icon={ faLightCoffee } />
While icons may be pre-rendered as HTML or rendered as DOM objects using abstracts, as in the above examples, they still depend upon the Font Awesome CSS being inserted into the DOM separately.
This is done automatically when the SVG with JavaScript technology is loaded via CDN or Kit. However, there's currently no built-in way to ensure that the Font Awesome CSS is inserted when Font Awesome is configured for Web Font technology.
The workarounds risk compatibility problems with other clients, and one of the main goals of this package is to solve such compatibility problems.
Workaround 1: bundle the fontawesome-svg-core
npm
npm install --save @fortawesome/fontawesome-svg-core
import { dom } from '@fortawesome/fontawesome-svg-core'
if ( !window.FontAwesome ) {
dom.insertCss(dom.css())
}
If your bundler does tree-shaking, then this should result in a pretty slim addition to your bundle--mostly the CSS content itself.
This approach is also susceptible to problems caused by differences in Font Awesome versions between the version of that npm package and the version used for generating the abstract with its classes.
Workaround 2: fetch the CSS appropriate for the version
Get the Font Awesome version currently loaded: fa()->version()
.
Fetch the required CSS from the CDN, replacing
the version number appropriately and set its contents as the text of a new
<style>
node, like this:
fetch('https://use.fontawesome.com/releases/v5.12.1/css/svg-with-js.css')
.then(response => response.ok ? response.text() : null)
.then(css => {
if( css ) {
const faCssStyle = document.createElement('STYLE')
faCssStyle.appendChild(document.createTextNode(css))
document.head.appendChild(faCssStyle)
} else {
// handle error
}
})
.catch(error => {
// handle error
})
You might also query the DOM first to make sure some other similar CSS hasn't already been added before adding this to the DOM yourself.
You may you want to use features like Power Transforms that are only available when
SVG technology is configured, or icon styles like Duotone that are only available
when Font Awesome Pro is configured, or some icons that are only available
in newer releases of Font Awesome. You can detect those configurations
using accessor methods on the FontAwesome
instance from your PHP code.
The FortAwesome\fa
function provides convenient access to the FontAwesome
singleton instance. The following examples assume that you've done a
use function FortAwesome\fa;
fa()->technology()
(svg or webfont)fa()->pro()
(boolean)fa()->pseudo_elements()
(boolean)fa()->v4_compatibility()
(boolean)fa()-version()
("latest" or something concrete like "5.12.0")
You can use these accessors when or after the font_awesome_enqueued
action
hook has been been triggered.
Refer to the PHP API documentation for details on these accessors and any others that be available.
What gets enqueued depends upon whether the WordPress site owner has configured Font Awesome to use the CDN or Kits. (A bit of a misnomer, since kits are loaded from CDN as well, just differently.)
A number of <script>
or <link>
resources are loaded, depending whether the
site owner configures for SVG or Web Font technology, and enables version 4
compatibility.
- main resource:
all.js
(SVG) orall.css
(Web Font) - v4 compatibility shims :
v4-shims.js
(SVG) orv4-shims.css
(Web Font) These shims are what version 4 icon classes to version 5 equivalents
Some additional inline resources may be added, depending on configuration:
- an inline
<script>
is added to enable pseudo-element support when SVG technology is configured. - an inline
<style>
is added to enable additional v4 compatibility support: shimming the v4font-family
name
If conflict detection is enabled, an additional <script>
is enqueued that loads
the conflict detector from the CDN.
When configured to use a kit, only the kit's loader <script>
is enqueued.
While the conflict scanner is enabled, an additional inline <script>
is added
to configure the conflict detector within the kit.
The kit loader script subsequently handles the insertion of various <script>
or <link>
elements, based on the kit's configuration, but that all happens
outside of WordPress semantics. As far as WordPress is concerned, it's just a
single wp_enqueue_script
on the kit loader.
The URLs loaded from the Font Awesome CDN are specific to a given release, so their contents don't change, and therefore, they can be long-term cached in the browser.
For example, suppose Font Awesome is configured for Free Web Font, version 5.12.1, then this will be the main resource loaded:
https://use.fontawesome.com/releases/v5.12.1/css/all.css
It's loaded as 56KB over the network, but on subsequent loads, it does not hit the network but loads from the browser's disk cache.
(The CSS also causes the underlying webfont files to be loaded. The story is the same, subsequent loads will normally use the browser's disk cache and not use the network.)
Given the large and growing number of icons availble in Font Awesome, it's natural to ask whether one might be able to load only the subset actually used.
In the WordPress ecosystem, though, it's common for site owners to install more than one theme or plugin that each uses Font Awesome icons, and tries to load its own version of Font Awesome. This causes conflicts across those various themes or plugins when activated on the same WordPress site.
A primary goal of this plugin package is to ease the pain for site owners to get those themes and plugins working with a single loaded version of Font Awesome that works for all concerned. And especially if it's a Font Awesome Pro user, they should be able to use Pro icons in their pages and posts, even while other installed plugins only use Free icons from version 4.
In that case where the site owner, their theme, and any number of installed plugins each use Font Awesome icons directly, it would be very difficult to determine what minimal subset could be created that would include all of the icons required by any of those clients.
Simply making all of them available for a given version of Font Awesome allows for every client to be satisfied.
Font Awesome Pro Kits (but not Free kits) have some built-in loading optimization that results in fewer resources being loaded, only as they are required by the browser.
Again, those resources will normally be long-term cached in the browser and loaded from the browser's disk cache on subsequent loads.
Pro SVG Kits are super-optimized. They auto-subset icon-by-icon. If a given web site only used one icon out of the 7,000+ in Font Awesome Pro, then only that one single icon would be fetched--except on subsequent loads when it would probably be pulled from disk cache.
Suppose you're in a situation like this:
- you are a developer
- you're also the WordPress site owner
- you control what themes or plugins are active on that site now and in the future
- you are comfortable working directly in source code to manage which version and technology of Font Awesome is loaded
- in the event that you do encounter an unexpected conflict, you are comfortable with investigating the WordPress resource queue and/or inspecting the browser DOM to identify and resolve the problem
- the advantages of creating a subset are more important to you than the advantages of loading
all.css
orall.js
from the Font Awesome CDN, or loading via Kit
In that case, then you might prefer to do a manual installation instead of using this plugin package.
You could either load exactly the resources you want from the Font Awesome CDN, or you could create your own subset of resources to load locally from your WordPress server or from your own CDN.
Font Awesome's Pro icon licensing does not allow theme or plugin vendors to distribute Font Awesome Pro to their users. However, if your user has enabled Font Awesome Pro on their WordPress site, then you can provide whatever functionality you like to aid the user's use of those Pro icons.
Some ways you could accomplish this:
- In your marketing materials, make it clear that your product enables a design experience with a Font Awesome Pro installation provided by the user
- Using this package, register a preference for pro in your
font_awesome_preferences
action hook. This will remind the user in the Font Awesome settings UI that your product wants Pro to be enabled. - Your code could detect that
fa()->pro()
is false and post an admin notice or other messaging in your own WordPress admin UI.
Once the site owner enables Pro, fa()->pro()
will be true
and your code can
then rely on the presence of Font Awesome Pro for the version indicated by
fa()->version()
.
(See the PHP API docs for how to resolve the symbolic
"latest"
version as a concrete version like "5.12.0"
.)
The Font Awesome GraphQL API allows you to query and search icon metadata.
See also documentation in PHP API on the FontAwesome::query()
method.
When you only need to query public fields, you can issue queries directly
against api.fontawesome.com
.
You could paste this into your browser's JavaScript console right now and get a list of all icon names in the 5.12.0 release:
fetch(
'https://api.fontawesome.com',
{
method: 'POST',
headers: {'Content-Type': 'application/json'},
body: '{"query": "query Icons($ver: String!) { release(version:$ver) { icons { id } } }", "variables": { "ver": "6.x" } }'
}
)
.then(response => response.ok ? response.json() : null)
.then(json => console.log(json))
.catch(e => console.error(e))
Queries that include field selections on fields requiring scopes more privileged than public require authorization with a Font Awesome account-holder's API Token.
There are some current and future Font Awesome features that require higher privileged scopes.
Currently, to query the kits on an account requires an API Token with the kits_read
scope. Normally, a plugin or theme you develop probably wouldn't need that particular
information, but it will serve as an example for how authorized queries can be issued
through the API REST controller provided by this package.
The following examples assume that you're using the apiFetch()
available
on the global wp
object in Gutenberg, or that you're using an apiFetch()
that you've
bundled and imported from @wordpress/api-fetch
,
and configured it with an appopriate REST root URL)
and nonce.
If you open your browser to a window in Gutenberg, such as on a new post, you could copy and paste these samples into the JavaScript console as-is.
First, for comparison, here's the same all-public query like we issued above, but this time through the Font Awesome REST API endpoint:
wp.apiFetch( {
path: '/font-awesome/v1/api',
method: 'POST',
body: 'query { release(version:"5.12.0") { icons { id } } }'
} ).then( res => {
console.log( res );
} )
Now this query requires no extra authentication work on your part, yet it allows you to issue a query that is authorized by the WordPress site owner's API Token, if configured:
wp.apiFetch( {
path: '/font-awesome/v1/api',
method: 'POST',
body: 'query { me { kits { token name } } }'
} ).then( res => {
console.log( res );
} )
There are several clients in this GitHub repo that demonstrate how your code can use this package:
Component | Description |
---|---|
integrations/themes/theme-alpha |
Theme accepts default requirements, but also conditionally uses Pro icons when available. It expects Font Awesome to be installed as a plugin by the site owner, rather than including it as a composer package. |
integrations/plugins/plugin-beta |
Plugin requires version 4 compatibility, webfont technology, and a specific version. Uses some version 4 icon names. Assumes this package is already installed as a plugin. |
integrations/plugins/plugin-sigma |
A plugin that requires this package via composer. |
See DEVELOPMENT.md for instructions on how you can set up a development environment to make contributions.