Skip to content

Supporting older versions of Safari on iOS

At the time of writing, the version of Alpine.js 3.12.3 bundled with Hyvä 1.3.0 supports Safari on iOS version 12.2 (released on 2019-03-25) and newer. The Tailwindcss classes used by Hyvä require Safari on iOS 14.5 (released on 2021-04-21).

Native Alpine.js 3.12.3 vs the Hyvä Bundle

The native version of Alpine.js 3.12.3 only supports Safari on iOS 13.4 (released on 2020-03-24), because of the use of the Nullish coalescing operator ??.

Hyvä 1.2.6 bundles a patched version of Alpine.js, which supports Safari on iOS 12.2.

Supporting older versions requires polyfilling JavaScript methods and updating some Tailwind classes in templates.

Alpine and Tailwind v2 versions of Hyvä

The easiest way to support older browsers is to build on a version of Hyvä that used Alpine.js and Tailwindcss v2.
At the time of writing, the latest release with Alpine.js and Tailwind v2 is 1.1.25.

No Support

Please be aware that we no longer support 1.1.x releases of Hyvä.
New features are developed only for releases based on Alpine v3 and Tailwind v3.

That said, building a theme based on an older Hyvä release can be a good choice, if support for older browsers is required and the existing feature set is sufficient.

queueMicrotask

Adding a polyfill for queueMicrotask will extend support to Safari on iOS 12.0.

For example:

<script>
if (typeof window.queueMicrotask !== 'function') {
    window.queueMicrotask = function(callback) {
        Promise.resolve()
            .then(callback)
            .catch(e => setTimeout(() => {
                throw e;
            }));
    };
}
</script>

Array flat and flatMap

Adding a polyfill for Array.prototype.flat and Array.prototype.flatMap will extend support to even older versions of Safari on iOS.

For example:

<script>
if (!Array.prototype.flat) {
    Object.defineProperty(Array.prototype, 'flat', {
        configurable: true,
        value: function flat () {
            var depth = isNaN(arguments[0]) ? 1 : Number(arguments[0]);

            return depth ? Array.prototype.reduce.call(this, function (acc, cur) {
                if (Array.isArray(cur)) {
                    acc.push.apply(acc, flat.call(cur, depth - 1));
                } else {
                    acc.push(cur);
                }

                return acc;
            }, []) : Array.prototype.slice.call(this);
        },
        writable: true
    });
}
if (!Array.prototype.flatMap) {
    Object.defineProperty(Array.prototype, 'flatMap', {
        configurable: true,
        value: function flatMap (callback) {
            return Array.prototype.map.apply(this, arguments).flat();
        },
        writable: true
    });
}
</script>

Required CSS changes

In addition to Alpine.js support, there also are changes required for styling.
Hyvä Tailwindcss uses the gap property on flexbox for styling in many templates with the Tailwind classes gap-x-2, gap-x-4, gap-y-0, gap-y-1, gap-y-2, gap-y-16.

The gap property for flexbox is supported by Safari for iOS since 14.5 (released on 26. April 2021).

class="flex gap-x-2"

To support older versions of Safari for IOS, change the Tailwindcss class to use the space property, for example space-x-2 amd space-y-2.
This applies to each use of gap-* together with flex.

class="flex space-x-2"

The space-* Tailwind classes translate to the css property margin, which is supported by all Safari on iOS versions.
Be sure to check the layout after each change and be prepared to make additional corrections if needed.

Adding content to the page <head>

If you need to support older versions, we recommend adding the polyfill code directly in the page <head>.
In order to render a template in the page <head>, a child needs to be declared for the head.additional block.

For example:

<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd"
>
    <body>
        <referenceContainer name="head.additional">
            <block name="head.alpinejs.polyfills" 
                   template="Magento_Theme::page/js/alpinejs-polyfills.phtml"/>
        </referenceContainer>
    </body>
</page>

Credits

Thanks to Regis Machado (sqli) for the help with the content of this page!

The polyfill implementations on this page were copied from jonathantneal/array-flat-polyfill, where they were released under the CC0 1.0 Universal (CC0 1.0) Public Domain Dedication license.