Adding Social Icons to Ghost

Adding Social Icons to Ghost

In the process of putting my fitness blog (back)together, I decided I was actually going to need to put the social icons in place. Especially if I wanted to make the most of it (secret plans in progress!).

In pretty much every other CMS, this is an incredibly simple process. For Ghost, however... It's an absolute ball ache that is far more complicated than it really needs to be. For the sake of simplifying it for myself when I update this blog, I decided to write it up.


There is some documentation on the Ghost site but the suggested site for SVG generation no longer seems to work and the example code really does seem to be an example, with icons not matching up to what they're supposed to be. I think the "Mastodon" entry was actually using the Pinterest icon as an example.

How to add social networks to your Ghost site - Tutorial
Add social networks like Instagram, LinkedIn, GitHub, Dribbble and other links to your Ghost site or blog by editing your theme.

Step 1:

To create all the links you need:

This bit is simple enough. Create whatever you need with the links they need on the admin dashboard.

Step 2

To start making changes to the theme. If using the default Casper theme (which in this case I am) then you can replace the code in site-nav.hbs with the following:

{{#if @site.secondary_navigation}}
    {{navigation type="secondary"}}
{{else}}
    <div class="social-links">
        {{#if @site.facebook}}
             <a class="social-link social-link-fb" href="{{facebook_url @site.facebook}}" title="Facebook" target="_blank" rel="noopener">{{> "icons/facebook"}}</a>
        {{/if}}
        {{#if @site.twitter}}
             <a class="social-link social-link-tw" href="{{twitter_url @site.twitter}}" title="Twitter" target="_blank" rel="noopener">{{> "icons/twitter"}}</a>
        {{/if}}
    </div>
    {{#unless @labs.members}}
        <a class="rss-button" href="https://feedly.com/i/subscription/feed/{{@site.url}}/rss/" title="RSS" target="_blank" rel="noopener">{{> "icons/rss"}}</a>
    {{/unless}}
{{/if}}

Next you need to create a new navigation.hbs file in the "partials" folder with the following:

{{#if isSecondary}}
    <ul class="nav">
        {{#foreach navigation}}
            <li class="nav-{{slug}}">
                <a href="{{url}}" class="social-link">
                    <svg width="16" height="16" role="img" aria-label="{{slug}} icon">
                        <use xlink:href="#{{slug}}"></use>
                    </svg>
                </a>
            </li>
        {{/foreach}}
    </ul>
{{else}}
    <ul class="nav">
        {{#foreach navigation}}
            <li class="{{link_class for=(url) class=(concat "nav-" slug)}}">
                <a href="{{url absolute="true"}}">{{label}}</a>
            </li>
        {{/foreach}}
    </ul>
{{/if}}

Step 3

Next up is getting our hands on the SVG icons that we need and translating that to sprites which can be used in the navigation.

You need to grab the icons you want from here: https://simpleicons.org/ and then upload them to here: https://svgsprite.com/tools/svg-sprite-generator/

Now, the output isn't going to be anywhere close to how you're going to need it for Ghost, so I chose to format the output as jsx as it was cleaner to see each icon entry (for me). Here's an example:

'mastodon': {
			width: 24,
			height: 24,
			viewBox: [0,0,24,24],
			data: '<path xmlns="http://www.w3.org/2000/svg" d="M23.193 7.879c0-5.206-3.411-6.732-3.411-6.732C18.062.357 15.108.025 12.041 0h-.076c-3.068.025-6.02.357-7.74 1.147 0 0-3.411 1.526-3.411 6.732 0 1.192-.023 2.618.015 4.129.124 5.092.934 10.109 5.641 11.355 2.17.574 4.034.695 5.535.612 2.722-.15 4.25-.972 4.25-.972l-.09-1.975s-1.945.613-4.129.539c-2.165-.074-4.449-.233-4.799-2.891a5.499 5.499 0 0 1-.048-.745s2.125.52 4.817.643c1.646.075 3.19-.097 4.758-.283 3.007-.359 5.625-2.212 5.954-3.905.517-2.665.475-6.507.475-6.507zm-4.024 6.709h-2.497V8.469c0-1.29-.543-1.944-1.628-1.944-1.2 0-1.802.776-1.802 2.312v3.349h-2.483v-3.35c0-1.536-.602-2.312-1.802-2.312-1.085 0-1.628.655-1.628 1.944v6.119H4.832V8.284c0-1.289.328-2.313.987-3.07.68-.758 1.569-1.146 2.674-1.146 1.278 0 2.246.491 2.886 1.474L12 6.585l.622-1.043c.64-.983 1.608-1.474 2.886-1.474 1.104 0 1.994.388 2.674 1.146.658.757.986 1.781.986 3.07v6.304z"/>'
		},

Now we need to put all this SVG info in to the default.hbs file immediately after the opening <body tag> in the following format with each entry between a <symbol> </symbol> and the relevant properties:

<svg width="0" height="0" class="hidden">
  <symbol viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg" id="mastodon">
      <title>Follow me on Mastodon</title>
      <path d="M23.193 7.879c0-5.206-3.411-6.732-3.411-6.732C18.062.357 15.108.025 12.041 0h-.076c-3.068.025-6.02.357-7.74 1.147 0 0-3.411 1.526-3.411 6.732 0 1.192-.023 2.618.015 4.129.124 5.092.934 10.109 5.641 11.355 2.17.574 4.034.695 5.535.612 2.722-.15 4.25-.972 4.25-.972l-.09-1.975s-1.945.613-4.129.539c-2.165-.074-4.449-.233-4.799-2.891a5.499 5.499 0 0 1-.048-.745s2.125.52 4.817.643c1.646.075 3.19-.097 4.758-.283 3.007-.359 5.625-2.212 5.954-3.905.517-2.665.475-6.507.475-6.507zm-4.024 6.709h-2.497V8.469c0-1.29-.543-1.944-1.628-1.944-1.2 0-1.802.776-1.802 2.312v3.349h-2.483v-3.35c0-1.536-.602-2.312-1.802-2.312-1.085 0-1.628.655-1.628 1.944v6.119H4.832V8.284c0-1.289.328-2.313.987-3.07.68-.758 1.569-1.146 2.674-1.146 1.278 0 2.246.491 2.886 1.474L12 6.585l.622-1.043c.64-.983 1.608-1.474 2.886-1.474 1.104 0 1.994.388 2.674 1.146.658.757.986 1.781.986 3.07v6.304z"></path>
  </symbol>
</svg>

As you can imagine, this can get pretty lengthy and feel rather intimidating

Step 4

It's finally time to package up the folder as a ZIP file and upload it to the admin portal, or upload the files to your server. The admin interface is easier.


Hopefully you didn't make a cock-up anywhere a long the line. If not, then it should look a little something like this:

Screenshot of social media icons

As I said at the start, an utter ball ache that personally I feel is something that really should be handled within the admin portal itself. Sure, there are a ridiculous number of social networks out there, but perhaps just adding a table with a box for "Name / Sprite info / link". Then you wouldn't have to consider every network but rather just pass that info in to the navigation file.

That's far beyond my skills however, but I don't think it should be part of theme customisation and simply hand waived away.

There are some real negatives to Ghost but I still like it... Mostly. It's becoming a true love/hate relationship.


Post Photo by NordWood Themes on Unsplash

Show Comments