aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorArmand Philippot <git@armandphilippot.com>2023-10-02 18:45:30 +0200
committerArmand Philippot <git@armandphilippot.com>2023-11-11 18:14:41 +0100
commitf914ff8376dd91c4f6f8ca149e1cb6becb622d88 (patch)
tree777dc0268eba86721878a715c68f0f09bedb4b18
parentb52b8183ce299b5a2d3c3b2f4f8cb94bb443d746 (diff)
refactor(components): rewrite Link component
* rename `external` prop to `isExternal` * rename `download` prop to `isDownload` * rewrite CSS to reduce code length and complexity * move link styles in Sass placeholders to avoid repeats because of WordPress articles * move NavLink component to molecules
-rw-r--r--.cspell/french-contents.txt5
-rw-r--r--.cspell/project-words.txt2
-rw-r--r--src/components/atoms/links/index.ts1
-rw-r--r--src/components/atoms/links/link.module.scss220
-rw-r--r--src/components/atoms/links/link.test.tsx10
-rw-r--r--src/components/atoms/links/link.tsx55
-rw-r--r--src/components/atoms/links/link/index.ts1
-rw-r--r--src/components/atoms/links/link/link.module.scss70
-rw-r--r--src/components/atoms/links/link/link.stories.tsx (renamed from src/components/atoms/links/link.stories.tsx)84
-rw-r--r--src/components/atoms/links/link/link.test.tsx47
-rw-r--r--src/components/atoms/links/link/link.tsx90
-rw-r--r--src/components/atoms/links/nav-link.test.tsx13
-rw-r--r--src/components/atoms/links/nav-link.tsx32
-rw-r--r--src/components/molecules/layout/branding.tsx3
-rw-r--r--src/components/molecules/layout/meta.tsx2
-rw-r--r--src/components/molecules/nav/index.ts1
-rw-r--r--src/components/molecules/nav/nav-link/index.ts1
-rw-r--r--src/components/molecules/nav/nav-link/nav-link.module.scss (renamed from src/components/atoms/links/nav-link.module.scss)40
-rw-r--r--src/components/molecules/nav/nav-link/nav-link.stories.tsx (renamed from src/components/atoms/links/nav-link.stories.tsx)36
-rw-r--r--src/components/molecules/nav/nav-link/nav-link.test.tsx28
-rw-r--r--src/components/molecules/nav/nav-link/nav-link.tsx44
-rw-r--r--src/components/molecules/nav/nav-list.module.scss10
-rw-r--r--src/components/molecules/nav/nav-list.tsx5
-rw-r--r--src/components/organisms/layout/comment.module.scss46
-rw-r--r--src/components/organisms/layout/summary.module.scss78
-rw-r--r--src/components/organisms/layout/summary.tsx8
m---------src/content0
-rw-r--r--src/pages/cv.tsx4
-rw-r--r--src/styles/abstracts/_placeholders.scss1
-rw-r--r--src/styles/abstracts/functions/_encode.scss2
-rw-r--r--src/styles/abstracts/placeholders/_links.scss102
-rw-r--r--src/styles/base/_typography.scss27
-rw-r--r--src/styles/pages/article.module.scss37
-rw-r--r--src/styles/pages/partials/_article-links.scss202
34 files changed, 692 insertions, 615 deletions
diff --git a/.cspell/french-contents.txt b/.cspell/french-contents.txt
index 1931b21..2d25575 100644
--- a/.cspell/french-contents.txt
+++ b/.cspell/french-contents.txt
@@ -1,6 +1,10 @@
Adwords
Auxseo
+Coreutils
+dotfiles
+dotig
GIDO
+htdocs
Jasson
Londe
Massena
@@ -12,3 +16,4 @@ référenceur
Superdoc
Symfony
webmarketing
+webroot
diff --git a/.cspell/project-words.txt b/.cspell/project-words.txt
index c9d6014..e2b983c 100644
--- a/.cspell/project-words.txt
+++ b/.cspell/project-words.txt
@@ -4,8 +4,10 @@ autodocs
changefreq
coldark
commitlint
+creativecommons
Eckles
formatjs
+gitlab
Gitlab
Jamstack
LINKEDIN
diff --git a/src/components/atoms/links/index.ts b/src/components/atoms/links/index.ts
index ad8824e..619f05c 100644
--- a/src/components/atoms/links/index.ts
+++ b/src/components/atoms/links/index.ts
@@ -1,4 +1,3 @@
export * from './link';
-export * from './nav-link';
export * from './sharing-link';
export * from './social-link';
diff --git a/src/components/atoms/links/link.module.scss b/src/components/atoms/links/link.module.scss
deleted file mode 100644
index 4980a1c..0000000
--- a/src/components/atoms/links/link.module.scss
+++ /dev/null
@@ -1,220 +0,0 @@
-@use "../../../styles/abstracts/functions" as fun;
-@use "../../../styles/abstracts/variables" as var;
-
-/* stylelint-disable no-descending-specificity */
-.link {
- &[hreflang] {
- &::after {
- display: inline-block;
-
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]";
- font-size: var(--font-size-sm);
- }
- }
-
- &--download {
- &::after {
- display: inline-block;
-
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_white}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
-
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_white}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
- }
- }
-
- &--external {
- &::after {
- display: inline-block;
-
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_white}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_white}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
- }
- }
-
- &--external#{&}--download {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_white}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_white}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_white}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_white}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
- }
- }
-}
-
-:global([data-theme="dark"]) {
- :local {
- .link {
- &--download {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_black}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
-
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_black}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
- }
- }
-
- &--external {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_black}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_black}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
- }
- }
-
- &--external.link--download {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_black}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_black}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_black}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_black}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
- }
- }
- }
- }
-}
-/* stylelint-enable no-descending-specificity */
diff --git a/src/components/atoms/links/link.test.tsx b/src/components/atoms/links/link.test.tsx
deleted file mode 100644
index 9829c1b..0000000
--- a/src/components/atoms/links/link.test.tsx
+++ /dev/null
@@ -1,10 +0,0 @@
-import { describe, expect, it } from '@jest/globals';
-import { render, screen } from '../../../../tests/utils';
-import { Link } from './link';
-
-describe('Link', () => {
- it('render a link', () => {
- render(<Link href="#">A link</Link>);
- expect(screen.getByRole('link')).toHaveTextContent('A link');
- });
-});
diff --git a/src/components/atoms/links/link.tsx b/src/components/atoms/links/link.tsx
deleted file mode 100644
index 1765bb5..0000000
--- a/src/components/atoms/links/link.tsx
+++ /dev/null
@@ -1,55 +0,0 @@
-import NextLink from 'next/link';
-import { AnchorHTMLAttributes, FC, ReactNode } from 'react';
-import styles from './link.module.scss';
-
-export type LinkProps = AnchorHTMLAttributes<HTMLAnchorElement> & {
- /**
- * The link body.
- */
- children: ReactNode;
- /**
- * True if it is a download link. Default: false.
- */
- download?: boolean;
- /**
- * True if it is an external link. Default: false.
- */
- external?: boolean;
- /**
- * The link target.
- */
- href: string;
- /**
- * The link target code language.
- */
- lang?: string;
-};
-
-/**
- * Link Component
- *
- * Render a link.
- */
-export const Link: FC<LinkProps> = ({
- children,
- className = '',
- download = false,
- external = false,
- href,
- lang,
- ...props
-}) => {
- const downloadClass = download ? styles['link--download'] : '';
- const linkClass = `${styles.link} ${downloadClass} ${className}`;
- const externalLinkClass = `${linkClass} ${styles['link--external']}`;
-
- return external ? (
- <a {...props} className={externalLinkClass} href={href} hrefLang={lang}>
- {children}
- </a>
- ) : (
- <NextLink {...props} className={linkClass} href={href} hrefLang={lang}>
- {children}
- </NextLink>
- );
-};
diff --git a/src/components/atoms/links/link/index.ts b/src/components/atoms/links/link/index.ts
new file mode 100644
index 0000000..e33728e
--- /dev/null
+++ b/src/components/atoms/links/link/index.ts
@@ -0,0 +1 @@
+export * from './link';
diff --git a/src/components/atoms/links/link/link.module.scss b/src/components/atoms/links/link/link.module.scss
new file mode 100644
index 0000000..8f94a54
--- /dev/null
+++ b/src/components/atoms/links/link/link.module.scss
@@ -0,0 +1,70 @@
+@use "../../../../styles/abstracts/placeholders";
+
+.link {
+ color: var(--color-primary);
+
+ &--regular {
+ @extend %link;
+ }
+
+ &[hreflang],
+ &--download,
+ &--external {
+ @extend %link-with-icon;
+ }
+
+ &[hreflang]:not(#{&}--download):not(#{&}--external) {
+ --is-icon-hidden: "";
+ }
+
+ &[hreflang] {
+ @extend %link-with-lang;
+ }
+
+ &--download {
+ @extend %download-link;
+ }
+
+ &--external {
+ @extend %external-link;
+ }
+
+ &--download,
+ &--external {
+ &:not([hreflang]) {
+ --is-lang-hidden: "";
+ }
+ }
+
+ &--external#{&}--download {
+ @extend %external-download-link;
+ }
+}
+
+:global([data-theme="light"]) {
+ :local {
+ .link {
+ &--download {
+ @extend %light-download-link;
+ }
+
+ &--external {
+ @extend %light-external-link;
+ }
+ }
+ }
+}
+
+:global([data-theme="dark"]) {
+ :local {
+ .link {
+ &--download {
+ @extend %dark-download-link;
+ }
+
+ &--external {
+ @extend %dark-external-link;
+ }
+ }
+ }
+}
diff --git a/src/components/atoms/links/link.stories.tsx b/src/components/atoms/links/link/link.stories.tsx
index 8351de7..0a6a6c5 100644
--- a/src/components/atoms/links/link.stories.tsx
+++ b/src/components/atoms/links/link/link.stories.tsx
@@ -1,11 +1,11 @@
-import { ComponentMeta, ComponentStory } from '@storybook/react';
+import type { ComponentMeta, ComponentStory } from '@storybook/react';
import { Link } from './link';
/**
* Link - Storybook Meta
*/
export default {
- title: 'Atoms/Typography/Links',
+ title: 'Atoms/Links/Link',
component: Link,
argTypes: {
children: {
@@ -31,7 +31,17 @@ export default {
required: false,
},
},
- download: {
+ href: {
+ control: {
+ type: 'text',
+ },
+ description: 'The link target.',
+ type: {
+ name: 'string',
+ required: true,
+ },
+ },
+ isDownload: {
control: {
type: 'boolean',
},
@@ -45,7 +55,7 @@ export default {
required: false,
},
},
- external: {
+ isExternal: {
control: {
type: 'boolean',
},
@@ -59,16 +69,6 @@ export default {
required: false,
},
},
- href: {
- control: {
- type: 'text',
- },
- description: 'The link target.',
- type: {
- name: 'string',
- required: true,
- },
- },
lang: {
control: {
type: 'text',
@@ -94,64 +94,62 @@ export const Default = Template.bind({});
Default.args = {
children: 'A link',
href: '#',
- download: false,
- external: false,
};
/**
* Links Stories - Download
*/
-export const Download = Template.bind({});
-Download.args = {
+export const DownloadLink = Template.bind({});
+DownloadLink.args = {
children: 'A link to a file',
href: '#',
- download: true,
- external: false,
+ isDownload: true,
+ isExternal: false,
};
/**
- * Links Stories - DownloadWithLang
+ * Links Stories - Download link with lang
*/
-export const DownloadWithLang = Template.bind({});
-DownloadWithLang.args = {
+export const DownloadLinkWithLang = Template.bind({});
+DownloadLinkWithLang.args = {
children: 'A link to a file',
href: '#',
- download: true,
- external: false,
+ isDownload: true,
+ isExternal: false,
lang: 'en',
};
/**
* Links Stories - External
*/
-export const External = Template.bind({});
-External.args = {
+export const ExternalLink = Template.bind({});
+ExternalLink.args = {
children: 'A link',
href: '#',
- download: false,
- external: true,
+ isDownload: false,
+ isExternal: true,
};
/**
- * Links Stories - External download
+ * Links Stories - External download link
*/
export const ExternalDownload = Template.bind({});
ExternalDownload.args = {
children: 'A link',
href: '#',
- download: true,
- external: true,
+ isDownload: true,
+ isExternal: true,
};
/**
- * Links Stories - External With Lang
+ * Links Stories - External link with Lang
*/
-export const ExternalWithLang = Template.bind({});
-ExternalWithLang.args = {
+export const ExternalLinkWithLang = Template.bind({});
+ExternalLinkWithLang.args = {
children: 'A link',
href: '#',
- download: false,
- external: true,
+ isDownload: false,
+ isExternal: true,
lang: 'en',
};
@@ -162,19 +160,19 @@ export const ExternalDownloadWithLang = Template.bind({});
ExternalDownloadWithLang.args = {
children: 'A link',
href: '#',
- download: true,
- external: true,
+ isDownload: true,
+ isExternal: true,
lang: 'en',
};
/**
* Links Stories - With Lang
*/
-export const WithLang = Template.bind({});
-WithLang.args = {
+export const LinkLang = Template.bind({});
+LinkLang.args = {
children: 'A link',
href: '#',
- download: false,
- external: false,
+ isDownload: false,
+ isExternal: false,
lang: 'en',
};
diff --git a/src/components/atoms/links/link/link.test.tsx b/src/components/atoms/links/link/link.test.tsx
new file mode 100644
index 0000000..ad1951d
--- /dev/null
+++ b/src/components/atoms/links/link/link.test.tsx
@@ -0,0 +1,47 @@
+import { describe, expect, it } from '@jest/globals';
+import { render, screen as rtlScreen } from '@testing-library/react';
+import { Link } from './link';
+
+describe('Link', () => {
+ it('renders a link', () => {
+ const anchor = 'porro';
+ const target = '/tempora';
+
+ render(<Link href={target}>{anchor}</Link>);
+
+ expect(rtlScreen.getByRole('link', { name: anchor })).toHaveAttribute(
+ 'href',
+ target
+ );
+ });
+
+ it('can render an external link', () => {
+ const anchor = 'accusamus';
+ const target = 'https://www.example.com';
+
+ render(
+ <Link href={target} isExternal>
+ {anchor}
+ </Link>
+ );
+
+ expect(rtlScreen.getByRole('link', { name: anchor })).toHaveClass(
+ 'link--external'
+ );
+ });
+
+ it('can render a download link', () => {
+ const anchor = 'dolor';
+ const target = '/officiis.pdf';
+
+ render(
+ <Link href={target} isDownload>
+ {anchor}
+ </Link>
+ );
+
+ expect(rtlScreen.getByRole('link', { name: anchor })).toHaveClass(
+ 'link--download'
+ );
+ });
+});
diff --git a/src/components/atoms/links/link/link.tsx b/src/components/atoms/links/link/link.tsx
new file mode 100644
index 0000000..e88cc7c
--- /dev/null
+++ b/src/components/atoms/links/link/link.tsx
@@ -0,0 +1,90 @@
+import NextLink from 'next/link';
+import {
+ forwardRef,
+ type AnchorHTMLAttributes,
+ type ForwardRefRenderFunction,
+ type ReactNode,
+} from 'react';
+import styles from './link.module.scss';
+
+export type LinkProps = Omit<
+ AnchorHTMLAttributes<HTMLAnchorElement>,
+ 'children' | 'download' | 'hrefLang' | 'lang'
+> & {
+ /**
+ * The link body.
+ */
+ children: ReactNode;
+ /**
+ * Should we disable the default transition on links?
+ *
+ * @default false
+ */
+ disableTransition?: boolean;
+ /**
+ * True if it is a download link.
+ *
+ * @default false
+ */
+ isDownload?: boolean;
+ /**
+ * True if it is an external link.
+ *
+ * @default false
+ */
+ isExternal?: boolean;
+ /**
+ * The link target.
+ */
+ href: string;
+ /**
+ * The link target code language.
+ */
+ lang?: string;
+};
+
+const LinkWithRef: ForwardRefRenderFunction<HTMLAnchorElement, LinkProps> = (
+ {
+ children,
+ className = '',
+ disableTransition = false,
+ isDownload = false,
+ isExternal = false,
+ href,
+ lang,
+ rel = '',
+ ...props
+ },
+ ref
+) => {
+ const LinkComponent = isExternal ? 'a' : NextLink;
+ const linkClass = [
+ styles.link,
+ styles[disableTransition ? '' : 'link--regular'],
+ styles[isDownload ? 'link--download' : ''],
+ styles[isExternal ? 'link--external' : ''],
+ className,
+ ].join(' ');
+ const linkRel =
+ isExternal && !rel.includes('external') ? `external ${rel}` : rel;
+
+ return (
+ <LinkComponent
+ {...props}
+ className={linkClass}
+ href={href}
+ hrefLang={lang}
+ ref={ref}
+ rel={linkRel}
+ >
+ {children}
+ </LinkComponent>
+ );
+};
+
+/**
+ * Link Component
+ *
+ * Render a link.
+ */
+export const Link = forwardRef(LinkWithRef);
diff --git a/src/components/atoms/links/nav-link.test.tsx b/src/components/atoms/links/nav-link.test.tsx
deleted file mode 100644
index acf3225..0000000
--- a/src/components/atoms/links/nav-link.test.tsx
+++ /dev/null
@@ -1,13 +0,0 @@
-import { describe, expect, it } from '@jest/globals';
-import { render, screen } from '../../../../tests/utils';
-import { NavLink } from './nav-link';
-
-describe('NavLink', () => {
- it('renders a nav link to blog page', () => {
- render(<NavLink href="/blog" label="Blog" />);
- expect(screen.getByRole('link', { name: 'Blog' })).toHaveAttribute(
- 'href',
- '/blog'
- );
- });
-});
diff --git a/src/components/atoms/links/nav-link.tsx b/src/components/atoms/links/nav-link.tsx
deleted file mode 100644
index 109529c..0000000
--- a/src/components/atoms/links/nav-link.tsx
+++ /dev/null
@@ -1,32 +0,0 @@
-import Link from 'next/link';
-import { FC, ReactNode } from 'react';
-import styles from './nav-link.module.scss';
-
-export type NavLinkProps = {
- /**
- * Link target.
- */
- href: string;
- /**
- * Link label.
- */
- label: string;
- /**
- * Link logo.
- */
- logo?: ReactNode;
-};
-
-/**
- * NavLink component
- *
- * Render a navigation link.
- */
-export const NavLink: FC<NavLinkProps> = ({ href, label, logo }) => {
- return (
- <Link className={styles.link} href={href}>
- {logo}
- {label}
- </Link>
- );
-};
diff --git a/src/components/molecules/layout/branding.tsx b/src/components/molecules/layout/branding.tsx
index 981da74..dceee5e 100644
--- a/src/components/molecules/layout/branding.tsx
+++ b/src/components/molecules/layout/branding.tsx
@@ -1,8 +1,7 @@
-import Link from 'next/link';
import { type FC, useRef } from 'react';
import { useIntl } from 'react-intl';
import { useStyles } from '../../../utils/hooks';
-import { Heading } from '../../atoms';
+import { Heading, Link } from '../../atoms';
import { FlippingLogo, type FlippingLogoProps } from '../images';
import styles from './branding.module.scss';
diff --git a/src/components/molecules/layout/meta.tsx b/src/components/molecules/layout/meta.tsx
index 094c420..63909a4 100644
--- a/src/components/molecules/layout/meta.tsx
+++ b/src/components/molecules/layout/meta.tsx
@@ -336,7 +336,7 @@ export const Meta: FC<MetaProps> = ({
);
case 'website':
return typeof value === 'string' ? (
- <Link href={value} external={true}>
+ <Link href={value} isExternal>
{value}
</Link>
) : null;
diff --git a/src/components/molecules/nav/index.ts b/src/components/molecules/nav/index.ts
index 9c46050..fe7cd0b 100644
--- a/src/components/molecules/nav/index.ts
+++ b/src/components/molecules/nav/index.ts
@@ -1,3 +1,4 @@
export * from './breadcrumb';
+export * from './nav-link';
export * from './nav-list';
export * from './pagination';
diff --git a/src/components/molecules/nav/nav-link/index.ts b/src/components/molecules/nav/nav-link/index.ts
new file mode 100644
index 0000000..f1b68c2
--- /dev/null
+++ b/src/components/molecules/nav/nav-link/index.ts
@@ -0,0 +1 @@
+export * from './nav-link';
diff --git a/src/components/atoms/links/nav-link.module.scss b/src/components/molecules/nav/nav-link/nav-link.module.scss
index e72885a..8a7d371 100644
--- a/src/components/atoms/links/nav-link.module.scss
+++ b/src/components/molecules/nav/nav-link/nav-link.module.scss
@@ -1,29 +1,39 @@
-@use "../../../styles/abstracts/functions" as fun;
-@use "../../../styles/abstracts/mixins" as mix;
-@use "../../../styles/abstracts/placeholders";
+@use "../../../../styles/abstracts/functions" as fun;
+@use "../../../../styles/abstracts/placeholders";
.link {
--draw-border-thickness: #{fun.convert-px(4)};
--draw-border-color1: var(--color-primary-light);
--draw-border-color2: var(--color-primary-lighter);
- display: inline-flex;
- flex-flow: column nowrap;
+ display: flex;
+ flex-flow: row wrap;
place-items: center;
place-content: center;
row-gap: var(--spacing-2xs);
- min-width: var(--link-min-width, fun.convert-px(85));
- padding: var(--spacing-xs);
- background: inherit;
+ min-width: var(--link-min-width, fun.convert-px(80));
+ padding: var(--spacing-xs) var(--spacing-xs) var(--spacing-2xs);
+ background: none;
+ border-radius: 8%;
font-size: var(--font-size-sm);
font-variant: small-caps;
font-weight: 600;
- line-height: 1;
+ text-align: center;
text-decoration: none;
- @include mix.media("screen") {
- @include mix.dimensions("md") {
- border-radius: 8%;
+ &--inline {
+ width: fit-content;
+
+ .logo {
+ margin-right: var(--spacing-xs);
+ }
+ }
+
+ &--stack {
+ .logo {
+ flex: 0 0 100%;
+ display: flex;
+ place-content: center;
}
}
@@ -32,6 +42,10 @@
@extend %draw-borders;
}
+ &:hover {
+ color: var(--color-primary-light);
+ }
+
&:focus {
color: var(--color-primary-light);
}
@@ -40,6 +54,8 @@
--draw-border-color1: var(--color-primary-dark);
--draw-border-color2: var(--color-primary-light);
+ color: var(--color-primary-dark);
+
@extend %draw-borders;
}
}
diff --git a/src/components/atoms/links/nav-link.stories.tsx b/src/components/molecules/nav/nav-link/nav-link.stories.tsx
index 7fca926..4e8400f 100644
--- a/src/components/atoms/links/nav-link.stories.tsx
+++ b/src/components/molecules/nav/nav-link/nav-link.stories.tsx
@@ -1,11 +1,12 @@
-import { ComponentMeta, ComponentStory } from '@storybook/react';
+import type { ComponentMeta, ComponentStory } from '@storybook/react';
+import { Icon } from '../../../atoms';
import { NavLink as NavLinkComponent } from './nav-link';
/**
* NavLink - Storybook Meta
*/
export default {
- title: 'Atoms/Typography/Links',
+ title: 'Molecules/Nav/NavLink',
component: NavLinkComponent,
argTypes: {
href: {
@@ -42,14 +43,37 @@ export default {
} as ComponentMeta<typeof NavLinkComponent>;
const Template: ComponentStory<typeof NavLinkComponent> = (args) => (
- <NavLinkComponent {...args} />
+ <div style={{ width: 'fit-content' }}>
+ <NavLinkComponent {...args} />
+ </div>
);
/**
- * Links Stories - Nav Link
+ * NavLink Stories - Default
*/
-export const NavLink = Template.bind({});
-NavLink.args = {
+export const Default = Template.bind({});
+Default.args = {
href: '#',
label: 'A nav link',
};
+
+/**
+ * NavLink Stories - StackWithLogo
+ */
+export const StackWithLogo = Template.bind({});
+StackWithLogo.args = {
+ href: '#example',
+ label: 'A nav link',
+ logo: <Icon aria-hidden shape="home" />,
+};
+
+/**
+ * NavLink Stories - InlineWithLogo
+ */
+export const InlineWithLogo = Template.bind({});
+InlineWithLogo.args = {
+ href: '#example',
+ isInline: true,
+ label: 'A nav link',
+ logo: <Icon aria-hidden shape="home" />,
+};
diff --git a/src/components/molecules/nav/nav-link/nav-link.test.tsx b/src/components/molecules/nav/nav-link/nav-link.test.tsx
new file mode 100644
index 0000000..aa9b557
--- /dev/null
+++ b/src/components/molecules/nav/nav-link/nav-link.test.tsx
@@ -0,0 +1,28 @@
+import { describe, expect, it } from '@jest/globals';
+import { render, screen as rtlScreen } from '@testing-library/react';
+import { NavLink } from './nav-link';
+
+describe('NavLink', () => {
+ it('renders a link', () => {
+ const label = 'eius';
+ const target = '#harum';
+
+ render(<NavLink href={target} label={label} />);
+
+ expect(rtlScreen.getByRole('link', { name: label })).toHaveAttribute(
+ 'href',
+ target
+ );
+ });
+
+ it('can render a nav link with inlined contents', () => {
+ const label = 'eius';
+ const target = '#harum';
+
+ render(<NavLink href={target} isInline label={label} />);
+
+ expect(rtlScreen.getByRole('link', { name: label })).toHaveClass(
+ 'link--inline'
+ );
+ });
+});
diff --git a/src/components/molecules/nav/nav-link/nav-link.tsx b/src/components/molecules/nav/nav-link/nav-link.tsx
new file mode 100644
index 0000000..f9fc529
--- /dev/null
+++ b/src/components/molecules/nav/nav-link/nav-link.tsx
@@ -0,0 +1,44 @@
+import {
+ type ForwardRefRenderFunction,
+ forwardRef,
+ type ReactNode,
+} from 'react';
+import { Link, type LinkProps } from '../../../atoms';
+import styles from './nav-link.module.scss';
+
+export type NavLinkProps = Omit<LinkProps, 'children' | 'disableTransition'> & {
+ /**
+ * Should the logo and label be inlined?
+ *
+ * @default false
+ */
+ isInline?: boolean;
+ /**
+ * The link label.
+ */
+ label: string;
+ /**
+ * The link logo.
+ */
+ logo?: ReactNode;
+};
+
+const NavLinkWithRef: ForwardRefRenderFunction<
+ HTMLAnchorElement,
+ NavLinkProps
+> = ({ className = '', isInline = false, label, logo, ...props }, ref) => {
+ const linkClass = [
+ styles.link,
+ styles[isInline ? 'link--inline' : 'link--stack'],
+ className,
+ ].join(' ');
+
+ return (
+ <Link {...props} className={linkClass} disableTransition ref={ref}>
+ {logo ? <span className={styles.logo}>{logo}</span> : null}
+ {label}
+ </Link>
+ );
+};
+
+export const NavLink = forwardRef(NavLinkWithRef);
diff --git a/src/components/molecules/nav/nav-list.module.scss b/src/components/molecules/nav/nav-list.module.scss
index ff99581..316638e 100644
--- a/src/components/molecules/nav/nav-list.module.scss
+++ b/src/components/molecules/nav/nav-list.module.scss
@@ -1,4 +1,14 @@
.nav {
+ &--main {
+ width: fit-content;
+ }
+
+ &--main & {
+ &__item {
+ flex: 1;
+ }
+ }
+
&--footer & {
&__item:not(:first-child) {
&::before {
diff --git a/src/components/molecules/nav/nav-list.tsx b/src/components/molecules/nav/nav-list.tsx
index 55c2aa9..b3c7138 100644
--- a/src/components/molecules/nav/nav-list.tsx
+++ b/src/components/molecules/nav/nav-list.tsx
@@ -1,5 +1,6 @@
import type { FC, ReactNode } from 'react';
-import { Link, List, ListItem, Nav, NavLink, type NavProps } from '../../atoms';
+import { Link, List, ListItem, Nav, type NavProps } from '../../atoms';
+import { NavLink } from './nav-link';
import styles from './nav-list.module.scss';
export type NavItem = {
@@ -49,7 +50,7 @@ export const NavList: FC<NavListProps> = ({
...props
}) => {
const kindClass = `nav--${kind}`;
- const navClass = `${styles[kindClass]} ${className}`;
+ const navClass = `${styles.nav} ${styles[kindClass]} ${className}`;
/**
* Get the nav items.
diff --git a/src/components/organisms/layout/comment.module.scss b/src/components/organisms/layout/comment.module.scss
index f645354..bf8aada 100644
--- a/src/components/organisms/layout/comment.module.scss
+++ b/src/components/organisms/layout/comment.module.scss
@@ -1,11 +1,13 @@
@use "../../../styles/abstracts/functions" as fun;
@use "../../../styles/abstracts/mixins" as mix;
+@use "../../../styles/abstracts/placeholders";
.wrapper {
padding: var(--spacing-md);
background: var(--color-bg);
border: fun.convert-px(1) solid var(--color-border);
- box-shadow: fun.convert-px(3) fun.convert-px(3) 0 0 var(--color-shadow-light),
+ box-shadow:
+ fun.convert-px(3) fun.convert-px(3) 0 0 var(--color-shadow-light),
fun.convert-px(4) fun.convert-px(4) fun.convert-px(3) fun.convert-px(-2)
var(--color-shadow);
@@ -50,7 +52,8 @@
height: fun.convert-px(85);
position: relative;
border-radius: fun.convert-px(3);
- box-shadow: 0 0 0 fun.convert-px(1) var(--color-shadow-light),
+ box-shadow:
+ 0 0 0 fun.convert-px(1) var(--color-shadow-light),
fun.convert-px(2) fun.convert-px(2) 0 fun.convert-px(1)
var(--color-shadow);
@@ -80,6 +83,45 @@
.body {
overflow-wrap: break-word;
+
+ :global {
+ a {
+ @extend %link;
+
+ &[hreflang],
+ &.download,
+ &.external {
+ @extend %link-with-icon;
+ }
+
+ &[hreflang] {
+ @extend %link-with-lang;
+ }
+
+ &[hreflang]:not(.download, .external) {
+ --is-icon-hidden: "";
+ }
+
+ &.download {
+ @extend %download-link;
+ }
+
+ &.external {
+ @extend %external-link;
+ }
+
+ &.download,
+ &.external {
+ &:not([hreflang]) {
+ --is-lang-hidden: "";
+ }
+ }
+
+ &.external.download {
+ @extend %external-download-link;
+ }
+ }
+ }
}
.footer {
diff --git a/src/components/organisms/layout/summary.module.scss b/src/components/organisms/layout/summary.module.scss
index 5052f73..b6cb4f4 100644
--- a/src/components/organisms/layout/summary.module.scss
+++ b/src/components/organisms/layout/summary.module.scss
@@ -1,5 +1,6 @@
@use "../../../styles/abstracts/functions" as fun;
@use "../../../styles/abstracts/mixins" as mix;
+@use "../../../styles/abstracts/placeholders";
.wrapper {
display: grid;
@@ -118,3 +119,80 @@
}
}
}
+
+.intro {
+ :global {
+ a {
+ @extend %link;
+
+ &[hreflang],
+ &.download,
+ &.external {
+ @extend %link-with-icon;
+ }
+
+ &[hreflang] {
+ @extend %link-with-lang;
+ }
+
+ &[hreflang]:not(.download, .external) {
+ --is-icon-hidden: "";
+ }
+
+ &.download {
+ @extend %download-link;
+ }
+
+ &.external {
+ @extend %external-link;
+ }
+
+ &.download,
+ &.external {
+ &:not([hreflang]) {
+ --is-lang-hidden: "";
+ }
+ }
+
+ &.external.download {
+ @extend %external-download-link;
+ }
+ }
+ }
+}
+
+:global([data-theme="light"]) {
+ :local {
+ .intro {
+ :global {
+ a {
+ &.download {
+ @extend %light-download-link;
+ }
+
+ &.external {
+ @extend %light-external-link;
+ }
+ }
+ }
+ }
+ }
+}
+
+:global([data-theme="dark"]) {
+ :local {
+ .intro {
+ :global {
+ a {
+ &.download {
+ @extend %dark-download-link;
+ }
+
+ &.external {
+ @extend %dark-external-link;
+ }
+ }
+ }
+ }
+ }
+}
diff --git a/src/components/organisms/layout/summary.tsx b/src/components/organisms/layout/summary.tsx
index d66af75..e21e4c7 100644
--- a/src/components/organisms/layout/summary.tsx
+++ b/src/components/organisms/layout/summary.tsx
@@ -117,9 +117,11 @@ export const Summary: FC<SummaryProps> = ({
</Link>
</header>
<div className={styles.body}>
- {/* eslint-disable-next-line react/no-danger -- Not safe but intro can
- * contains links or formatting so we need it. */}
- <div dangerouslySetInnerHTML={{ __html: intro }} />
+ <div
+ className={styles.intro}
+ // eslint-disable-next-line react/no-danger
+ dangerouslySetInnerHTML={{ __html: intro }}
+ />
<ButtonLink className={styles['read-more']} to={url}>
<>
{readMore}
diff --git a/src/content b/src/content
-Subproject c7236df956a4f9e242126540c175ac5dfd0b9c7
+Subproject 0a5267ca7df1b6600741aa172ffdfe7b4f762d9
diff --git a/src/pages/cv.tsx b/src/pages/cv.tsx
index 5882ff6..b23c7a2 100644
--- a/src/pages/cv.tsx
+++ b/src/pages/cv.tsx
@@ -38,7 +38,7 @@ const ExternalLink = ({
href = '',
...props
}: AnchorHTMLAttributes<HTMLAnchorElement>) => (
- <Link {...props} external={true} href={href}>
+ <Link {...props} isExternal href={href}>
{children}
</Link>
);
@@ -172,7 +172,7 @@ const CVPage: NextPageWithLayout = () => {
},
{
link: (chunks: ReactNode) => (
- <Link download={true} href={file}>
+ <Link href={file} isDownload>
{chunks}
</Link>
),
diff --git a/src/styles/abstracts/_placeholders.scss b/src/styles/abstracts/_placeholders.scss
index c978f96..04522d7 100644
--- a/src/styles/abstracts/_placeholders.scss
+++ b/src/styles/abstracts/_placeholders.scss
@@ -3,4 +3,5 @@
@forward "./placeholders/clearfix";
@forward "./placeholders/headings";
@forward "./placeholders/layout";
+@forward "./placeholders/links";
@forward "./placeholders/lists";
diff --git a/src/styles/abstracts/functions/_encode.scss b/src/styles/abstracts/functions/_encode.scss
index 4350185..388d106 100644
--- a/src/styles/abstracts/functions/_encode.scss
+++ b/src/styles/abstracts/functions/_encode.scss
@@ -4,7 +4,7 @@
/// @param {String} $svg A complete svg (`<svg>...</svg>`).
/// @return The encoded svg, ready to use for background-image.
@function encode-svg($svg) {
- $svg-encoding: (("<", "%3C"), (">", "%3E"), ("#", "%23"));
+ $svg-encoding: (('"', "'"), ("<", "%3C"), (">", "%3E"), ("#", "%23"));
@each $char, $encoded in $svg-encoding {
$svg: fun.str-replace($svg, $char, $encoded);
diff --git a/src/styles/abstracts/placeholders/_links.scss b/src/styles/abstracts/placeholders/_links.scss
new file mode 100644
index 0000000..a230e70
--- /dev/null
+++ b/src/styles/abstracts/placeholders/_links.scss
@@ -0,0 +1,102 @@
+@use "../../abstracts/functions" as fun;
+@use "../../abstracts/variables" as var;
+
+%link {
+ background: linear-gradient(to top, var(--color-primary) 50%, transparent 50%)
+ 0 0 / 100% 201% no-repeat;
+ color: var(--color-primary);
+ text-decoration-thickness: 0.15em;
+ text-underline-offset: 20%;
+ transition:
+ all 0.3s linear 0s,
+ text-decoration 0.18s ease-in-out 0s;
+
+ &:hover {
+ color: var(--color-primary-light);
+ text-decoration-thickness: 0.25em;
+ }
+
+ &:focus {
+ background-position: 0 100%;
+ color: var(--color-fg-inverted);
+ }
+
+ &:active {
+ background-position: 0 0;
+ color: var(--color-primary-dark);
+ text-decoration-thickness: 18%;
+ }
+}
+
+%link-with-icon {
+ &::after {
+ display: inline-block;
+ content: var(--is-lang-hidden, "\0000a0" var(--lang-icon, ""))
+ var(--is-icon-hidden, "\0000a0" var(--link-icon, ""));
+ font-size: var(--font-size-sm);
+ }
+}
+
+%link-with-lang {
+ --lang-icon: "[" attr(hreflang) "]";
+}
+
+%light-download-link {
+ // Prettier is removing spacing between attributes.
+ // prettier-ignore
+ --download-icon: url('#{fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z" /><path fill="#{var.$light-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z" /></svg>')}');
+
+ &:focus:not(:active) {
+ // Prettier is removing spacing between attributes.
+ // prettier-ignore
+ --download-icon: url('#{fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z" /><path fill="#{var.$light-theme_white}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z" /></svg>')}');
+ }
+}
+
+%dark-download-link {
+ // Prettier is removing spacing between attributes.
+ // prettier-ignore
+ --download-icon: url('#{fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z" /><path fill="#{var.$dark-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z" /></svg>')}');
+
+ &:focus:not(:active) {
+ // Prettier is removing spacing between attributes.
+ // prettier-ignore
+ --download-icon: url('#{fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z" /><path fill="#{var.$dark-theme_black}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z" /></svg>')}');
+ }
+}
+
+%light-external-link {
+ // Prettier is removing spacing between attributes.
+ // prettier-ignore
+ --external-icon: url('#{fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>')}');
+
+ &:focus:not(:active) {
+ // Prettier is removing spacing between attributes.
+ // prettier-ignore
+ --external-icon: url('#{fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_white}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>')}');
+ }
+}
+
+%dark-external-link {
+ // Prettier is removing spacing between attributes.
+ // prettier-ignore
+ --external-icon: url('#{fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>')}');
+
+ &:focus:not(:active) {
+ // Prettier is removing spacing between attributes.
+ // prettier-ignore
+ --external-icon: url('#{fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_black}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>')}');
+ }
+}
+
+%download-link {
+ --link-icon: var(--download-icon);
+}
+
+%external-link {
+ --link-icon: var(--external-icon);
+}
+
+%external-download-link {
+ --link-icon: var(--download-icon) "\0000a0" var(--external-icon);
+}
diff --git a/src/styles/base/_typography.scss b/src/styles/base/_typography.scss
index c98533e..170f246 100644
--- a/src/styles/base/_typography.scss
+++ b/src/styles/base/_typography.scss
@@ -9,33 +9,6 @@ small {
font-size: var(--font-size-sm);
}
-a {
- background: linear-gradient(to top, var(--color-primary) 50%, transparent 50%)
- 0 0 / 100% 201% no-repeat;
- color: var(--color-primary);
- text-decoration-thickness: 0.15em;
- text-underline-offset: 20%;
- transition:
- all 0.3s linear 0s,
- text-decoration 0.18s ease-in-out 0s;
-
- &:hover {
- color: var(--color-primary-light);
- text-decoration-thickness: 0.25em;
- }
-
- &:focus {
- background-position: 0 100%;
- color: var(--color-fg-inverted);
- }
-
- &:active {
- background-position: 0 0;
- color: var(--color-primary-dark);
- text-decoration-thickness: 18%;
- }
-}
-
button,
input,
optgroup,
diff --git a/src/styles/pages/article.module.scss b/src/styles/pages/article.module.scss
index 088718f..068826f 100644
--- a/src/styles/pages/article.module.scss
+++ b/src/styles/pages/article.module.scss
@@ -1,5 +1,6 @@
@use "../abstracts/functions" as fun;
@use "../abstracts/mixins" as mix;
+@use "../abstracts/placeholders";
@use "partials/article-headings";
@use "partials/article-links";
@use "partials/article-lists";
@@ -28,6 +29,42 @@
}
}
+:global([data-theme="light"]) {
+ :local {
+ .body {
+ :global {
+ a {
+ &.download {
+ @extend %light-download-link;
+ }
+
+ &.external {
+ @extend %light-external-link;
+ }
+ }
+ }
+ }
+ }
+}
+
+:global([data-theme="dark"]) {
+ :local {
+ .body {
+ :global {
+ a {
+ &.download {
+ @extend %dark-download-link;
+ }
+
+ &.external {
+ @extend %dark-external-link;
+ }
+ }
+ }
+ }
+ }
+}
+
.widget {
@include mix.media("screen") {
@include mix.dimensions("md") {
diff --git a/src/styles/pages/partials/_article-links.scss b/src/styles/pages/partials/_article-links.scss
index e88b81e..1627220 100644
--- a/src/styles/pages/partials/_article-links.scss
+++ b/src/styles/pages/partials/_article-links.scss
@@ -1,204 +1,40 @@
-@use "../../abstracts/functions" as fun;
-@use "../../abstracts/variables" as var;
+@use "../../abstracts/placeholders";
@mixin styles {
a {
- &[hreflang] {
- &::after {
- display: inline-block;
-
- /* Prettier is removing spacing between content parts. */
+ @extend %link;
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]";
- font-size: var(--font-size-sm);
- }
- }
- }
-
- /* stylelint-disable no-descending-specificity */
- a.download {
- &::after {
- display: inline-block;
-
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_white}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
+ &[hreflang],
+ &.download,
+ &.external {
+ @extend %link-with-icon;
}
&[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
- }
- }
-
- a.external {
- &::after {
- display: inline-block;
-
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
+ @extend %link-with-lang;
}
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_white}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
+ &[hreflang]:not(.download, .external) {
+ --is-icon-hidden: "";
}
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_white}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
+ &.download {
+ @extend %download-link;
}
- }
- a.external.download {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
+ &.external {
+ @extend %external-link;
}
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$light-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$light-theme_white}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$light-theme_white}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
+ &.download,
+ &.external {
+ &:not([hreflang]) {
+ --is-lang-hidden: "";
}
}
- }
-
- [data-theme="dark"] {
- a.download {
- &::after {
- /* Prettier is removing spacing between content parts. */
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_black}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
-
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_black}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>'));
- }
- }
- }
-
- a.external {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_black}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_black}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
- }
- }
-
- a.external.download {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_black}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_black}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &[hreflang] {
- &::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_blue}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_blue}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_blue}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
-
- &:focus:not(:active)::after {
- /* Prettier is removing spacing between content parts. */
-
- /* prettier-ignore */
- content: "\0000a0[" attr(hreflang) "]\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="m49 80.048-28.445-30.77 19.32 4.095V5.06h18.252v48.313l21.318-4.095z"/><path fill="#{var.$dark-theme_black}" d="M0 67.57v27.37h100V67.57H87.973v15.344H12.027V67.569z"/></svg>')) "\0000a0" url(fun.encode-svg('<svg width="13" viewBox="0 0 100 100" xmlns="http://www.w3.org/2000/svg"><path fill="#{var.$dark-theme_black}" d="M100 0 59.543 5.887l20.8 6.523-51.134 51.134 7.249 7.248L87.59 19.66l6.522 20.798z"/><path fill="#{var.$dark-theme_black}" d="M4 10a4 4 0 0 0-4 4v82a4 4 0 0 0 4 4h82a4 4 0 0 0 4-4V62.314h-8V92H8V18h29.686v-8z"/></svg>'));
- }
- }
+ &.external.download {
+ @extend %external-download-link;
}
}
}
-/* stylelint-enable no-descending-specificity */