{"id":3315,"date":"2019-12-01T15:41:10","date_gmt":"2019-12-01T13:41:10","guid":{"rendered":"https:\/\/blog.tomayac.com\/2019\/12\/01\/animated-svg-favicons\/"},"modified":"2019-12-01T15:41:10","modified_gmt":"2019-12-01T13:41:10","slug":"animated-svg-favicons","status":"publish","type":"post","link":"https:\/\/tomayac.com\/wordpress\/2019\/12\/01\/animated-svg-favicons\/","title":{"rendered":"Animated SVG favicons"},"content":{"rendered":"\n\t\t\t<p>When it comes to animating SVGs, there're three options: using\n<abbr title=\"Cascading Style Sheets\">CSS<\/abbr>,\n<abbr title=\"JavaScript\">JS<\/abbr>, or\n<abbr title=\"Synchronized Multimedia Integration Language\">SMIL<\/abbr>.\nEach comes with its own pros and cons, whose discussion is beyond the scope of this article,\nbut <a href=\"https:\/\/www.sarasoueidan.com\/\">Sara Soueidan<\/a> has a great\n<a href=\"https:\/\/theblog.adobe.com\/the-state-of-svg-animation\">article<\/a> on the topic.\nIn this post, I add a repeating <em>shrink<\/em> animation to a circle with all three methods,\nand then try to use these SVGs as favicons.<\/p>\n<h2 id=\"animating-svg-with-css\">Animating SVG with CSS <a class=\"direct-link\" href=\"https:\/\/blog.tomayac.com\/2019\/12\/01\/animated-svg-favicons\/#animating-svg-with-css\">\u2693<\/a><\/h2>\n<p>Here's an example of animating an SVG with CSS based on the\n<a href=\"https:\/\/developer.mozilla.org\/en-US\/docs\/Web\/CSS\/animation\"><code>animation<\/code><\/a> and the\n<a href=\"https:\/\/developer.mozilla.org\/en-US\/docs\/Web\/CSS\/transform\"><code>transform<\/code><\/a> properties.\nI scale the circle from the center and repeat the animation forever:<\/p>\n<pre class=\"language-html\"><code class=\"language-html\"><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;<\/span>svg<\/span> <span class=\"token attr-name\">viewBox<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>0 0 100 100<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">xmlns<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>http:\/\/www.w3.org\/2000\/svg<span class=\"token punctuation\">\"<\/span><\/span><span class=\"token punctuation\">><\/span><\/span><br>  <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;<\/span>style<\/span><span class=\"token punctuation\">><\/span><\/span><span class=\"token style\"><span class=\"token language-css\"><br>    <span class=\"token selector\">svg<\/span> <span class=\"token punctuation\">{<\/span><br>      <span class=\"token property\">max-width<\/span><span class=\"token punctuation\">:<\/span> 100px<span class=\"token punctuation\">;<\/span><br>    <span class=\"token punctuation\">}<\/span><br><br>    <span class=\"token selector\">circle<\/span> <span class=\"token punctuation\">{<\/span><br>      <span class=\"token property\">display<\/span><span class=\"token punctuation\">:<\/span> block<span class=\"token punctuation\">;<\/span><br>      <span class=\"token property\">animation<\/span><span class=\"token punctuation\">:<\/span> 2s linear infinite both circle-animation<span class=\"token punctuation\">;<\/span><br>      <span class=\"token property\">transform-origin<\/span><span class=\"token punctuation\">:<\/span> 50% 50%<span class=\"token punctuation\">;<\/span><br>    <span class=\"token punctuation\">}<\/span><br><br>    <span class=\"token atrule\"><span class=\"token rule\">@keyframes<\/span> circle-animation<\/span> <span class=\"token punctuation\">{<\/span><br>      <span class=\"token selector\">0%<\/span> <span class=\"token punctuation\">{<\/span><br>        <span class=\"token property\">transform<\/span><span class=\"token punctuation\">:<\/span> <span class=\"token function\">scale<\/span><span class=\"token punctuation\">(<\/span>1<span class=\"token punctuation\">)<\/span><span class=\"token punctuation\">;<\/span><br>      <span class=\"token punctuation\">}<\/span><br>      <span class=\"token selector\">100%<\/span> <span class=\"token punctuation\">{<\/span><br>        <span class=\"token property\">transform<\/span><span class=\"token punctuation\">:<\/span> <span class=\"token function\">scale<\/span><span class=\"token punctuation\">(<\/span>0<span class=\"token punctuation\">)<\/span><span class=\"token punctuation\">;<\/span><br>      <span class=\"token punctuation\">}<\/span><br>    <span class=\"token punctuation\">}<\/span><br>  <\/span><\/span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;\/<\/span>style<\/span><span class=\"token punctuation\">><\/span><\/span><br>  <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;<\/span>circle<\/span> <span class=\"token attr-name\">fill<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>red<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">cx<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>50<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">cy<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>50<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">r<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>45<span class=\"token punctuation\">\"<\/span><\/span><span class=\"token punctuation\">\/><\/span><\/span><br><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;\/<\/span>svg<\/span><span class=\"token punctuation\">><\/span><\/span><\/code><\/pre>\n<h2 id=\"animating-svg-with-js\">Animating SVG with JS <a class=\"direct-link\" href=\"https:\/\/blog.tomayac.com\/2019\/12\/01\/animated-svg-favicons\/#animating-svg-with-js\">\u2693<\/a><\/h2>\n<p>The <a href=\"https:\/\/developer.mozilla.org\/en-US\/docs\/Web\/SVG\/Element\/script\">SVG <code>&lt;script&gt;<\/code><\/a>\ntag allows to add scripts to an SVG document.\nIt has some <a href=\"https:\/\/svgwg.org\/svg2-draft\/interact.html#ScriptElement\">subtle differences<\/a>\nto the regular HTML <code>&lt;script&gt;<\/code>, for example, it uses the <code>href<\/code> instead of the <code>src<\/code> attribute,\nbut above all it's important to know that any functions defined within any <code>&lt;script&gt;<\/code> tag\nhave a <em>global scope<\/em> across the entire current document.\nBelow, you can see an SVG script used to reduce the radius of the circle until it's equal to zero,\nthen reset it to the initial value, and finally repeat this forever.<\/p>\n<pre class=\"language-html\"><code class=\"language-html\"><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;<\/span>svg<\/span> <span class=\"token attr-name\">viewBox<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>0 0 100 100<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">xmlns<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>http:\/\/www.w3.org\/2000\/svg<span class=\"token punctuation\">\"<\/span><\/span><span class=\"token punctuation\">><\/span><\/span><br>  <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;<\/span>circle<\/span> <span class=\"token attr-name\">fill<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>blue<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">cx<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>50<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">cy<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>50<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">r<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>45<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token punctuation\">\/><\/span><\/span><br>  <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;<\/span>script<\/span> <span class=\"token attr-name\">type<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>text\/javascript<span class=\"token punctuation\">\"<\/span><\/span><span class=\"token punctuation\">><\/span><\/span><span class=\"token script\"><span class=\"token included-cdata\"><span class=\"token cdata\">&lt;![CDATA[<\/span><span class=\"token language-javascript\"><br>    <span class=\"token keyword\">const<\/span> circle <span class=\"token operator\">=<\/span> document<span class=\"token punctuation\">.<\/span><span class=\"token function\">querySelector<\/span><span class=\"token punctuation\">(<\/span><span class=\"token string\">'circle'<\/span><span class=\"token punctuation\">)<\/span><span class=\"token punctuation\">;<\/span><br>    <span class=\"token keyword\">let<\/span> r <span class=\"token operator\">=<\/span> <span class=\"token number\">45<\/span><span class=\"token punctuation\">;<\/span><br>    <span class=\"token keyword\">const<\/span> <span class=\"token function-variable function\">animate<\/span> <span class=\"token operator\">=<\/span> <span class=\"token punctuation\">(<\/span><span class=\"token punctuation\">)<\/span> <span class=\"token operator\">=><\/span> <span class=\"token punctuation\">{<\/span><br>      circle<span class=\"token punctuation\">.<\/span><span class=\"token function\">setAttribute<\/span><span class=\"token punctuation\">(<\/span><span class=\"token string\">'r'<\/span><span class=\"token punctuation\">,<\/span> r<span class=\"token operator\">--<\/span><span class=\"token punctuation\">)<\/span><span class=\"token punctuation\">;<\/span><br>      <span class=\"token keyword\">if<\/span> <span class=\"token punctuation\">(<\/span>r <span class=\"token operator\">===<\/span> <span class=\"token number\">0<\/span><span class=\"token punctuation\">)<\/span> <span class=\"token punctuation\">{<\/span><br>        r <span class=\"token operator\">=<\/span> <span class=\"token number\">45<\/span><span class=\"token punctuation\">;<\/span><br>      <span class=\"token punctuation\">}<\/span><br>      <span class=\"token function\">requestAnimationFrame<\/span><span class=\"token punctuation\">(<\/span>animate<span class=\"token punctuation\">)<\/span><span class=\"token punctuation\">;<\/span><br>    <span class=\"token punctuation\">}<\/span><span class=\"token punctuation\">;<\/span><br>    <span class=\"token function\">requestAnimationFrame<\/span><span class=\"token punctuation\">(<\/span>animate<span class=\"token punctuation\">)<\/span><span class=\"token punctuation\">;<\/span><br>  <\/span><span class=\"token cdata\">]]><\/span><\/span><\/span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;\/<\/span>script<\/span><span class=\"token punctuation\">><\/span><\/span><br><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;\/<\/span>svg<\/span><span class=\"token punctuation\">><\/span><\/span><\/code><\/pre>\n<h2 id=\"animating-svg-with-smil\">Animating SVG with SMIL <a class=\"direct-link\" href=\"https:\/\/blog.tomayac.com\/2019\/12\/01\/animated-svg-favicons\/#animating-svg-with-smil\">\u2693<\/a><\/h2>\n<p>The last example uses SMIL, where, via the\n<a href=\"https:\/\/developer.mozilla.org\/en-US\/docs\/Web\/SVG\/SVG_animation_with_SMIL\"><code>&lt;animate&gt;<\/code><\/a>\ntag inside of the <code>&lt;circle&gt;<\/code> tag, I declaratively describe that I want to\nanimate the circle's <code>r<\/code> attribute (that determines the radius) and repeat it indefinitely.<\/p>\n<pre class=\"language-html\"><code class=\"language-html\"><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;<\/span>svg<\/span> <span class=\"token attr-name\">viewBox<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>0 0 100 100<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">xmlns<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>http:\/\/www.w3.org\/2000\/svg<span class=\"token punctuation\">\"<\/span><\/span><span class=\"token punctuation\">><\/span><\/span><br>  <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;<\/span>circle<\/span> <span class=\"token attr-name\">fill<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>green<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">cx<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>50<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">cy<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>50<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">r<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>45<span class=\"token punctuation\">\"<\/span><\/span><span class=\"token punctuation\">><\/span><\/span><br>    <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;<\/span>animate<\/span> <span class=\"token attr-name\">attributeName<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>r<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">from<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>45<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">to<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>0<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">dur<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>2s<span class=\"token punctuation\">\"<\/span><\/span> <span class=\"token attr-name\">repeatCount<\/span><span class=\"token attr-value\"><span class=\"token punctuation\">=<\/span><span class=\"token punctuation\">\"<\/span>indefinite<span class=\"token punctuation\">\"<\/span><\/span><span class=\"token punctuation\">\/><\/span><\/span><br>  <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;\/<\/span>circle<\/span><span class=\"token punctuation\">><\/span><\/span><br><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;\/<\/span>svg<\/span><span class=\"token punctuation\">><\/span><\/span><\/code><\/pre>\n<h2 id=\"using-animated-svgs-as-images\">Using Animated SVGs as Images <a class=\"direct-link\" href=\"https:\/\/blog.tomayac.com\/2019\/12\/01\/animated-svg-favicons\/#using-animated-svgs-as-images\">\u2693<\/a><\/h2>\n<p>Before using animated SVGs as favicons, I want to briefly discuss\nhow you can use each of the three examples on a website.\nAgain there're three options: referenced via the <code>src<\/code> attribute of an <code>&lt;img&gt;<\/code> tag,\nin an <code>&lt;iframe&gt;<\/code>, or inlined in the main document.\nAgain, SVG scripts have access to the <em>global scope<\/em>, so they should definitely be used with care.\nSome user agents, for example, Google Chrome, don't run scripts for SVGs in <code>&lt;img&gt;<\/code>.\nThe <a href=\"https:\/\/glitch.com\/~animated-svg-favicon\">Glitch<\/a> embedded below shows all variants in action.\nMy recommendation would be to stick with CSS animations whenever you can,\nsince it's the most compatible and future-proof variant.<\/p>\n<div class=\"glitch-embed-wrap\" style=\"height: 420px; width: 100%;\">\n  <iframe src=\"https:\/\/glitch.com\/embed\/#!\/embed\/animated-svg-favicon?path=icon_js.svg&previewSize=100\" title=\"animated-svg-favicon on Glitch\" allow=\"geolocation; microphone; camera; midi; vr; encrypted-media\" style=\"height: 100%; width: 100%; border: 0;\" loading=\"lazy\">\n  <\/iframe>\n<\/div>\n<h2 id=\"using-animated-svgs-as-favicons\">Using Animated SVGs as Favicons <a class=\"direct-link\" href=\"https:\/\/blog.tomayac.com\/2019\/12\/01\/animated-svg-favicons\/#using-animated-svgs-as-favicons\">\u2693<\/a><\/h2>\n<p>Since <a href=\"https:\/\/crbug.com\/294179\">crbug.com\/294179<\/a> is fixed, Chrome <em>finally<\/em> supports SVG favicons,\nalongside <a href=\"https:\/\/caniuse.com\/#feat=link-icon-svg\">many other browsers<\/a>.\nI have recently successfully experimented with\n<a href=\"https:\/\/blog.tomayac.com\/2019\/09\/21\/prefers-color-scheme-in-svg-favicons-for-dark-mode-icons\/\"><code>prefers-color-scheme<\/code> in SVG favicons<\/a>,\nso I wanted to see if animated SVGs work, too.\nLong story short, it seems only Firefox supports them at the time of writing,\nand only favicons that are animated with either CSS or JS.\nYou can see this working in Firefox in the screencast embedded below.\nIf you open my <a href=\"https:\/\/animated-svg-favicon.glitch.me\/\">Glitch demo<\/a> in a standalone window,\nyou can test this yourself with the radio buttons at the top.<\/p>\n<iframe width=\"560\" height=\"315\" src=\"https:\/\/www.youtube-nocookie.com\/embed\/SlesN-eGdIE\" frameborder=\"0\" allow=\"accelerometer; autoplay; encrypted-media; gyroscope; picture-in-picture\" allowfullscreen=\"\" loading=\"lazy\"><\/iframe>\n<p>Should you use this in practice?\nProbably not, since it can be really distracting.\nIt might be useful as a progressive enhancement to show activity during a short period of time,\nfor example, while a web application is busy with processing data.\nBefore considering to use this, I would definitely recommend taking the user's\n<a href=\"https:\/\/developers.google.com\/web\/updates\/2019\/03\/prefers-reduced-motion\"><code>prefers-reduced-motion<\/code><\/a>\npreferences into account.<\/p>\n\n\t\t\t<p>\n\t\t\t\t<img alt=\"Thomas Steiner\" width=\"32\" height=\"32\" src=\"https:\/\/blog.tomayac.com\/feed.php?dl=https%3A%2F%2Fblog.tomayac.com%2F2019%2F12%2F01%2Fanimated-svg-favicons%2F&dp=%2F2019%2F12%2F01%2Fanimated-svg-favicons%2F&dt=Animated%20SVG%20favicons\" alt=\"\">\n\t\t\t\t<br\/>This post appeared first on <a href=\"https:\/\/blog.tomayac.com\/2019\/12\/01\/animated-svg-favicons\/\">https:\/\/blog.tomayac.com\/2019\/12\/01\/animated-svg-favicons\/<\/a>.\n\t\t\t<\/p>\n\t\t","protected":false},"excerpt":{"rendered":"<p>\t\t\tWhen it comes to animating SVGs, there&#8217;re three options: using<br \/>\nCSS,<br \/>\nJS, or<br \/>\nSMIL.<br \/>\nEach comes with its own pros and cons, whose discussion is beyond the scope of this article,<br \/>\nbut Sara Soueidan has a great<br \/>\narticle on the topic.<br \/>\nIn this post, I add a &#8230;<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"intlwemo_wallet_address":"","footnotes":""},"categories":[],"tags":[],"class_list":["post-3315","post","type-post","status-publish","format-standard","hentry"],"_links":{"self":[{"href":"https:\/\/tomayac.com\/wordpress\/wp-json\/wp\/v2\/posts\/3315","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/tomayac.com\/wordpress\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/tomayac.com\/wordpress\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/tomayac.com\/wordpress\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/tomayac.com\/wordpress\/wp-json\/wp\/v2\/comments?post=3315"}],"version-history":[{"count":3,"href":"https:\/\/tomayac.com\/wordpress\/wp-json\/wp\/v2\/posts\/3315\/revisions"}],"predecessor-version":[{"id":3328,"href":"https:\/\/tomayac.com\/wordpress\/wp-json\/wp\/v2\/posts\/3315\/revisions\/3328"}],"wp:attachment":[{"href":"https:\/\/tomayac.com\/wordpress\/wp-json\/wp\/v2\/media?parent=3315"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/tomayac.com\/wordpress\/wp-json\/wp\/v2\/categories?post=3315"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/tomayac.com\/wordpress\/wp-json\/wp\/v2\/tags?post=3315"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}