From b9caf8eedb4856fb26f5a9bf5a38ae21b2502cab Mon Sep 17 00:00:00 2001 From: Rubens Jean Simon <93041872+rubemoon@users.noreply.github.com> Date: Tue, 13 Aug 2024 04:48:24 +0000 Subject: [PATCH] fix: update layout and import Chirpy template files --- _config.yml | 2 +- _data/contact.yml | 7 +- _data/locales/ar.yml | 91 + _data/locales/bg-BG.yml | 81 + _data/locales/cs-CZ.yml | 89 + _data/locales/de-DE.yml | 87 + _data/locales/el-GR.yml | 91 + _data/locales/en.yml | 91 + _data/locales/es-ES.yml | 77 + _data/locales/fi-FI.yml | 90 + _data/locales/fr-FR.yml | 77 + _data/locales/hu-HU.yml | 79 + _data/locales/id-ID.yml | 77 + _data/locales/it-IT.yml | 90 + _data/locales/ko-KR.yml | 84 + _data/locales/my-MM.yml | 77 + _data/locales/pt-BR.yml | 77 + _data/locales/ru-RU.yml | 87 + _data/locales/sl-SI.yml | 91 + _data/locales/sv-SE.yml | 91 + _data/locales/th.yml | 91 + _data/locales/tr-TR.yml | 77 + _data/locales/uk-UA.yml | 77 + _data/locales/vi-VN.yml | 76 + _data/locales/zh-CN.yml | 83 + _data/locales/zh-TW.yml | 83 + _data/origin/basic.yml | 46 + _data/origin/cors.yml | 59 + _data/share.yml | 2 +- _includes/analytics/cloudflare.html | 7 + _includes/analytics/goatcounter.html | 6 + _includes/analytics/google.html | 13 + _includes/analytics/matomo.html | 14 + _includes/analytics/umami.html | 6 + _includes/comments.html | 5 + _includes/comments/disqus.html | 50 + _includes/comments/giscus.html | 71 + _includes/comments/utterances.html | 49 + _includes/datetime.html | 20 + _includes/embed/audio.html | 35 + _includes/embed/bilibili.html | 9 + _includes/embed/twitch.html | 8 + _includes/embed/video.html | 59 + _includes/embed/youtube.html | 9 + _includes/favicons.html | 2 +- _includes/footer.html | 11 +- _includes/goatcounter.html | 8 + _includes/google-analytics.html | 14 + _includes/head.html | 107 ++ _includes/img-url.html | 39 + _includes/js-selector.html | 106 ++ _includes/jsdelivr-combine.html | 26 + _includes/lang.html | 10 + _includes/language-alias.html | 70 + _includes/media-url.html | 37 + _includes/mermaid.html | 62 + _includes/metadata-hook.html | 1 + _includes/mode-toggle.html | 116 ++ _includes/no-linenos.html | 10 + _includes/notification.html | 24 + _includes/origin-type.html | 13 + _includes/pageviews/goatcounter.html | 19 + _includes/post-description.html | 16 + _includes/post-nav.html | 34 + _includes/post-paginator.html | 91 + _includes/post-sharing.html | 52 + _includes/read-time.html | 37 + _includes/refactor-content.html | 255 +++ _includes/related-posts.html | 94 + _includes/search-loader.html | 47 + _includes/search-results.html | 10 + _includes/sidebar.html | 99 ++ _includes/toc.html | 13 + _includes/topbar.html | 77 + _includes/trending-tags.html | 46 + _includes/update-list.html | 40 + _javascript/categories.js | 7 + _javascript/commons.js | 5 + _javascript/home.js | 8 + _javascript/misc.js | 7 + _javascript/modules/components/back-to-top.js | 19 + .../modules/components/category-collapse.js | 36 + _javascript/modules/components/clipboard.js | 143 ++ _javascript/modules/components/img-loading.js | 67 + _javascript/modules/components/img-popup.js | 48 + .../modules/components/locale-datetime.js | 53 + .../modules/components/mode-watcher.js | 14 + .../modules/components/search-display.js | 110 ++ _javascript/modules/components/sidebar.js | 27 + _javascript/modules/components/toc.js | 15 + .../modules/components/tooltip-loader.js | 11 + _javascript/modules/layouts.js | 3 + _javascript/modules/layouts/basic.js | 7 + _javascript/modules/layouts/sidebar.js | 7 + _javascript/modules/layouts/topbar.js | 5 + _javascript/modules/plugins.js | 6 + _javascript/page.js | 9 + _javascript/post.js | 17 + _javascript/pwa/app.js | 51 + _javascript/pwa/sw.js | 94 + _layouts/compress.html | 4 +- _layouts/default.html | 16 +- _layouts/home.html | 7 +- _layouts/post.html | 21 +- _sass/addon/commons.scss | 1532 +++++++++++++++++ _sass/addon/module.scss | 204 +++ _sass/addon/syntax.scss | 292 ++++ _sass/addon/variables.scss | 33 + _sass/colors/syntax-dark.scss | 164 ++ _sass/colors/syntax-light.scss | 210 +++ _sass/colors/typography-dark.scss | 147 ++ _sass/colors/typography-light.scss | 112 ++ _sass/layout/archives.scss | 144 ++ _sass/layout/categories.scss | 83 + _sass/layout/category-tag.scss | 72 + _sass/layout/home.scss | 189 ++ _sass/layout/post.scss | 370 ++++ _sass/layout/tags.scss | 19 + _sass/main.bundle.scss | 2 + _sass/main.scss | 13 + _sass/variables-hook.scss | 3 + assets/404.html | 14 + assets/css/jekyll-theme-chirpy.scss | 10 + assets/feed.xml | 61 + assets/js/data/mathjax.js | 25 + assets/js/data/search.json | 20 + assets/js/data/swconf.js | 47 + assets/robots.txt | 10 + 128 files changed, 8636 insertions(+), 34 deletions(-) create mode 100644 _data/locales/ar.yml create mode 100644 _data/locales/bg-BG.yml create mode 100644 _data/locales/cs-CZ.yml create mode 100644 _data/locales/de-DE.yml create mode 100644 _data/locales/el-GR.yml create mode 100644 _data/locales/en.yml create mode 100644 _data/locales/es-ES.yml create mode 100644 _data/locales/fi-FI.yml create mode 100644 _data/locales/fr-FR.yml create mode 100644 _data/locales/hu-HU.yml create mode 100644 _data/locales/id-ID.yml create mode 100644 _data/locales/it-IT.yml create mode 100644 _data/locales/ko-KR.yml create mode 100644 _data/locales/my-MM.yml create mode 100644 _data/locales/pt-BR.yml create mode 100644 _data/locales/ru-RU.yml create mode 100644 _data/locales/sl-SI.yml create mode 100644 _data/locales/sv-SE.yml create mode 100644 _data/locales/th.yml create mode 100644 _data/locales/tr-TR.yml create mode 100644 _data/locales/uk-UA.yml create mode 100644 _data/locales/vi-VN.yml create mode 100644 _data/locales/zh-CN.yml create mode 100644 _data/locales/zh-TW.yml create mode 100644 _data/origin/basic.yml create mode 100644 _data/origin/cors.yml create mode 100644 _includes/analytics/cloudflare.html create mode 100644 _includes/analytics/goatcounter.html create mode 100644 _includes/analytics/google.html create mode 100644 _includes/analytics/matomo.html create mode 100644 _includes/analytics/umami.html create mode 100644 _includes/comments.html create mode 100644 _includes/comments/disqus.html create mode 100644 _includes/comments/giscus.html create mode 100644 _includes/comments/utterances.html create mode 100644 _includes/datetime.html create mode 100644 _includes/embed/audio.html create mode 100644 _includes/embed/bilibili.html create mode 100644 _includes/embed/twitch.html create mode 100644 _includes/embed/video.html create mode 100644 _includes/embed/youtube.html create mode 100644 _includes/goatcounter.html create mode 100644 _includes/google-analytics.html create mode 100644 _includes/head.html create mode 100644 _includes/img-url.html create mode 100644 _includes/js-selector.html create mode 100644 _includes/jsdelivr-combine.html create mode 100644 _includes/lang.html create mode 100644 _includes/language-alias.html create mode 100644 _includes/media-url.html create mode 100644 _includes/mermaid.html create mode 100644 _includes/metadata-hook.html create mode 100644 _includes/mode-toggle.html create mode 100644 _includes/no-linenos.html create mode 100644 _includes/notification.html create mode 100644 _includes/origin-type.html create mode 100644 _includes/pageviews/goatcounter.html create mode 100644 _includes/post-description.html create mode 100644 _includes/post-nav.html create mode 100644 _includes/post-paginator.html create mode 100644 _includes/post-sharing.html create mode 100644 _includes/read-time.html create mode 100644 _includes/refactor-content.html create mode 100644 _includes/related-posts.html create mode 100644 _includes/search-loader.html create mode 100644 _includes/search-results.html create mode 100644 _includes/sidebar.html create mode 100644 _includes/toc.html create mode 100644 _includes/topbar.html create mode 100644 _includes/trending-tags.html create mode 100644 _includes/update-list.html create mode 100644 _javascript/categories.js create mode 100644 _javascript/commons.js create mode 100644 _javascript/home.js create mode 100644 _javascript/misc.js create mode 100644 _javascript/modules/components/back-to-top.js create mode 100644 _javascript/modules/components/category-collapse.js create mode 100644 _javascript/modules/components/clipboard.js create mode 100644 _javascript/modules/components/img-loading.js create mode 100644 _javascript/modules/components/img-popup.js create mode 100644 _javascript/modules/components/locale-datetime.js create mode 100644 _javascript/modules/components/mode-watcher.js create mode 100644 _javascript/modules/components/search-display.js create mode 100644 _javascript/modules/components/sidebar.js create mode 100644 _javascript/modules/components/toc.js create mode 100644 _javascript/modules/components/tooltip-loader.js create mode 100644 _javascript/modules/layouts.js create mode 100644 _javascript/modules/layouts/basic.js create mode 100644 _javascript/modules/layouts/sidebar.js create mode 100644 _javascript/modules/layouts/topbar.js create mode 100644 _javascript/modules/plugins.js create mode 100644 _javascript/page.js create mode 100644 _javascript/post.js create mode 100644 _javascript/pwa/app.js create mode 100644 _javascript/pwa/sw.js create mode 100644 _sass/addon/commons.scss create mode 100644 _sass/addon/module.scss create mode 100644 _sass/addon/syntax.scss create mode 100644 _sass/addon/variables.scss create mode 100644 _sass/colors/syntax-dark.scss create mode 100644 _sass/colors/syntax-light.scss create mode 100644 _sass/colors/typography-dark.scss create mode 100644 _sass/colors/typography-light.scss create mode 100644 _sass/layout/archives.scss create mode 100644 _sass/layout/categories.scss create mode 100644 _sass/layout/category-tag.scss create mode 100644 _sass/layout/home.scss create mode 100644 _sass/layout/post.scss create mode 100644 _sass/layout/tags.scss create mode 100644 _sass/main.bundle.scss create mode 100644 _sass/main.scss create mode 100644 _sass/variables-hook.scss create mode 100644 assets/404.html create mode 100644 assets/css/jekyll-theme-chirpy.scss create mode 100644 assets/feed.xml create mode 100644 assets/js/data/mathjax.js create mode 100644 assets/js/data/search.json create mode 100644 assets/js/data/swconf.js create mode 100644 assets/robots.txt diff --git a/_config.yml b/_config.yml index acf754c..7b59a1b 100644 --- a/_config.yml +++ b/_config.yml @@ -9,7 +9,7 @@ theme: jekyll-theme-chirpy lang: en # Change to your timezone › https://kevinnovak.github.io/Time-Zone-Picker -timezone: +timezone: America/Sao_Paulo # jekyll-seo-tag settings › https://github.com/jekyll/jekyll-seo-tag/blob/master/docs/usage.md # ↓ -------------------------- diff --git a/_data/contact.yml b/_data/contact.yml index c253abd..246727c 100644 --- a/_data/contact.yml +++ b/_data/contact.yml @@ -21,16 +21,13 @@ - type: rss icon: "fas fa-rss" noblank: true + # Uncomment and complete the url below to enable more contact options # # - type: mastodon # icon: 'fab fa-mastodon' # icons powered by # url: '' # Fill with your Mastodon account page, rel="me" will be applied for verification -# -# - type: linkedin -# icon: 'fab fa-linkedin' # icons powered by -# url: '' # Fill with your Linkedin homepage -# + # - type: stack-overflow # icon: 'fab fa-stack-overflow' # url: '' # Fill with your stackoverflow homepage diff --git a/_data/locales/ar.yml b/_data/locales/ar.yml new file mode 100644 index 0000000..c608298 --- /dev/null +++ b/_data/locales/ar.yml @@ -0,0 +1,91 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: منشور + category: فئة + tag: وسم + +# The tabs of sidebar +tabs: + # format: : + home: الرئيسية + categories: الفئات + tags: الوسوم + archives: الأرشيف + about: حول + +# the text displayed in the search bar & search results +search: + hint: بحث + cancel: إلغاء + no_results: نأسف! لا يوجد نتائج. + +panel: + lastmod: المحدثة مؤخرا + trending_tags: الوسوم الشائعة + toc: محتويات + +copyright: + # Shown at the bottom of the post + license: + template: هذا المنشور تحت ترخيص :LICENSE_NAME بواسطة المؤلف. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: بعض الحقوق محفوظة. + verbose: >- + ما لم يذكر خلاف ذلك ، يتم ترخيص منشورات المدونة على هذا الموقع + بموجب ترخيص Creative Commons Attribution 4.0 International (CC BY 4.0) من قبل المؤلف. + +meta: باستخدام :PLATFORM السمة :THEME + +not_found: + statment: عذرا, الرابط التالي غير صالح أو انه يشير إلى صفحة غير موجودة. + +notification: + update_found: يتوفر اصدار جديد للمحتوى. + update: تحديث + +# ----- Posts related labels ----- + +post: + written_by: بواسطة + posted: نشّر + updated: حدّث + words: كلمات + pageview_measure: مشاهدات + read_time: + unit: دقيقة + prompt: قراءة + relate_posts: إقرأ المزيد + share: شارك + button: + next: الأجدد + previous: الأقدم + copy_code: + succeed: تم النسخ! + share_link: + title: أنسخ الرابط + succeed: تم نسخ الرابط بنجاح! + +# Date time format. +# See: , +df: + post: + strftime: "%b %e, %Y" + dayjs: "ll" + archives: + strftime: "%b" + dayjs: "MMM" + +# categories page +categories: + category_measure: + singular: فئة + plural: فئات + post_measure: + singular: منشور + plural: منشورات diff --git a/_data/locales/bg-BG.yml b/_data/locales/bg-BG.yml new file mode 100644 index 0000000..3e04993 --- /dev/null +++ b/_data/locales/bg-BG.yml @@ -0,0 +1,81 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Публикация + category: Категория + tag: Таг + +# The tabs of sidebar +tabs: + # format: : + home: Начало + categories: Категории + tags: Тагове + archives: Архив + about: За мен + +# the text displayed in the search bar & search results +search: + hint: търси + cancel: Отмени + no_results: Упс! Не са намерени резултати. + +panel: + lastmod: Наскоро обновени + trending_tags: Популярни тагове + toc: Съдържание + +copyright: + # Shown at the bottom of the post + license: + template: Тази публикация е лицензирана под :LICENSE_NAME от автора. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Някои права запазени. + verbose: >- + Освен ако не е посочено друго, публикациите в блога на този сайт са лицензирани + под лиценза Creative Commons Attribution 4.0 (CC BY 4.0) от автора. + +meta: Създадено чрез :PLATFORM и :THEME тема + +not_found: + statment: Съжалявам, но на този URL адрес няма налично съдържание. + +notification: + update_found: Налична е нова версия на съдържанието. + update: Обнови + +# ----- Posts related labels ----- + +post: + written_by: Автор + posted: Публикувана + updated: Обновена + words: думи + pageview_measure: преглеждания + read_time: + unit: мин + prompt: четиво + relate_posts: Още за четене + share: Споделете + button: + next: По-нови + previous: По-стари + copy_code: + succeed: Копирано! + share_link: + title: Копирай линк + succeed: Линкът е копиран успешно! + +# categories page +categories: + category_measure: + singular: категория + plural: категории + post_measure: + singular: публикация + plural: публикации diff --git a/_data/locales/cs-CZ.yml b/_data/locales/cs-CZ.yml new file mode 100644 index 0000000..e515c08 --- /dev/null +++ b/_data/locales/cs-CZ.yml @@ -0,0 +1,89 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Příspěvek + category: Kategorie + tag: Štítek + +# The tabs of sidebar +tabs: + # format: : + home: Domů + categories: Kategorie + tags: Štítky + archives: Archivy + about: O mně + +# the text displayed in the search bar & search results +search: + hint: hledat + cancel: Zrušit + no_results: Ups! Žádný výsledek nenalezen. + +panel: + lastmod: Nedávno aktualizováno + trending_tags: Trendy štítky + toc: Obsah + +copyright: + # Shown at the bottom of the post + license: + template: Tento příspěvek je licencován pod :LICENSE_NAME autorem. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Některá práva vyhrazena. + verbose: >- + Pokud není uvedeno jinak, jsou příspěvky na tomto webu licencovány + pod licencí Creative Commons Attribution 4.0 International (CC BY 4.0) Licence autora. + +meta: Použití :PLATFORM s motivem :THEME + +not_found: + statment: Omlouváme se, adresu URL jsme špatně umístili nebo odkazuje na něco, co neexistuje. + +notification: + update_found: Je k dispozici nová verze obsahu. + update: Aktualizace + +# ----- Posts related labels ----- + +post: + written_by: Od + posted: Zveřejněno + updated: Aktualizováno + words: slova + pageview_measure: zhlednutí + read_time: + unit: minut + prompt: čtení + relate_posts: Další čtení + share: Sdílet + button: + next: Novější + previous: Starší + copy_code: + succeed: Zkopírováno! + share_link: + title: Kopírovat odkaz + succeed: Zkopírováno! + +# Date time format. +# See: , +df: + post: + strftime: "%b %e, %Y" + dayjs: "ll" + archives: + strftime: "%b" + dayjs: "MMM" + +# categories page +categories: + category_measure: kategorie + post_measure: + singular: příspěvěk + plural: příspěvky diff --git a/_data/locales/de-DE.yml b/_data/locales/de-DE.yml new file mode 100644 index 0000000..6b187b4 --- /dev/null +++ b/_data/locales/de-DE.yml @@ -0,0 +1,87 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Eintrag + category: Kategorie + tag: Tag + +# The tabs of sidebar +tabs: + # format: : + home: Startseite + categories: Kategorien + tags: Tags + archives: Archiv + about: Über + +# the text displayed in the search bar & search results +search: + hint: Suche + cancel: Abbrechen + no_results: Ups! Keine Einträge gefunden. + +panel: + lastmod: Kürzlich aktualisiert + trending_tags: Beliebte Tags + toc: Inhalt + +copyright: + # Shown at the bottom of the post + license: + template: Dieser Eintrag ist vom Autor unter :LICENSE_NAME lizensiert. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Einige Rechte vorbehalten. + verbose: >- + Alle Einträge auf dieser Seite stehen, soweit nicht anders angegeben, unter der Lizenz Creative Commons Attribution 4.0 (CC BY 4.0). + +meta: Powered by :PLATFORM with :THEME theme + +not_found: + statment: Entschuldigung, dieser Link verweist auf keine vorhandene Ressource. + +notification: + update_found: Eine neue Version ist verfügbar. + update: Neue Version + +# ----- Posts related labels ----- + +post: + written_by: Von + posted: Veröffentlicht + updated: Aktualisiert + words: Wörter + pageview_measure: Aufrufe + read_time: + unit: Minuten + prompt: Lesezeit + relate_posts: Weiterlesen + share: Teilen + button: + next: Nächster Eintrag + previous: Eintrag vorher + copy_code: + succeed: Kopiert! + share_link: + title: Link kopieren + succeed: Link erfolgreich kopiert! + +# Date time format. +# See: , +df: + post: + strftime: "%d.%m.%Y" + dayjs: "DD.MM.YYYY" + +# categories page +categories: + category_measure: + singular: Kategorie + plural: Kategorien + post_measure: + singular: Eintrag + plural: Einträge diff --git a/_data/locales/el-GR.yml b/_data/locales/el-GR.yml new file mode 100644 index 0000000..ab5fb0e --- /dev/null +++ b/_data/locales/el-GR.yml @@ -0,0 +1,91 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Δημοσίευση + category: Κατηγορία + tag: Ετικέτα + +# The tabs of sidebar +tabs: + # format: : + home: Home + categories: Κατηγορίες + tags: Ετικέτες + archives: Αρχεία + about: Σχετικά + +# the text displayed in the search bar & search results +search: + hint: αναζήτηση + cancel: Ακύρωση + no_results: Oops! Κανένα αποτέλεσμα δεν βρέθηκε. + +panel: + lastmod: Σχετικά ενημερωμένα + trending_tags: Ετικέτες τάσης + toc: Περιεχόμενα + +copyright: + # Shown at the bottom of the post + license: + template: Η δημοσίευση αυτή βρίσκεται υπο την άδεια :LICENSE_NAME Greekforce1821. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Ορισμένα δικαιώματα reserved. + verbose: >- + Εκτός αλλού ή οπουδήποτε αλλού, τα blog posts σε αυτήν την σελίδα βρίσκονται υπο την άδεια + Creative Commons Attribution 4.0 International (CC BY 4.0) του δημιουργού. + +meta: Αξιοποιώντας την :PLATFORM theme :THEME + +not_found: + statment: Συγνώμη, έχουμε τοποθετήσει λάθος αυτήν την διεύθυνση URL ή υποδεικνύει κάτι που δεν υπάρχει. + +notification: + update_found: Υπάρχει διαθέσιμη μια νέα έκδοση του περιεχομένου. + update: Ενημέρωση + +# ----- Posts related labels ----- + +post: + written_by: Από + posted: Δημοσιεύθηκε + updated: Ενημερώθηκε + words: λέξεις + pageview_measure: προβολές + read_time: + unit: Λεπτά + prompt: διαβάσματος + relate_posts: Περισσότερα + share: Κοινοποιήστε + button: + next: Νεότερα + previous: Παλαιότερα + copy_code: + succeed: Αντιγράφθηκε! + share_link: + title: Αντιγραφή συνδέσμου + succeed: Η διεύθυνση αντιγράφθηκε με επιτυχία! + +# Date time format. +# See: , +df: + post: + strftime: "%b %e, %Y" + dayjs: "ll" + archives: + strftime: "%b" + dayjs: "MMM" + +# categories page +categories: + category_measure: + singular: Κατηγορία + plural: Κατηγορίες + post_measure: + singular: Δημοσίευση + plural: Δημοσιεύσεις diff --git a/_data/locales/en.yml b/_data/locales/en.yml new file mode 100644 index 0000000..0dbe713 --- /dev/null +++ b/_data/locales/en.yml @@ -0,0 +1,91 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Post + category: Category + tag: Tag + +# The tabs of sidebar +tabs: + # format: : + home: Home + categories: Categories + tags: Tags + archives: Archives + about: About + +# the text displayed in the search bar & search results +search: + hint: search + cancel: Cancel + no_results: Oops! No results found. + +panel: + lastmod: Recently Updated + trending_tags: Trending Tags + toc: Contents + +copyright: + # Shown at the bottom of the post + license: + template: This post is licensed under :LICENSE_NAME by the author. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Some rights reserved. + verbose: >- + Except where otherwise noted, the blog posts on this site are licensed + under the Creative Commons Attribution 4.0 International (CC BY 4.0) License by the author. + +meta: Using the :THEME theme for :PLATFORM. + +not_found: + statment: Sorry, we've misplaced that URL or it's pointing to something that doesn't exist. + +notification: + update_found: A new version of content is available. + update: Update + +# ----- Posts related labels ----- + +post: + written_by: By + posted: Posted + updated: Updated + words: words + pageview_measure: views + read_time: + unit: min + prompt: read + relate_posts: Further Reading + share: Share + button: + next: Newer + previous: Older + copy_code: + succeed: Copied! + share_link: + title: Copy link + succeed: Link copied successfully! + +# Date time format. +# See: , +df: + post: + strftime: "%b %e, %Y" + dayjs: "ll" + archives: + strftime: "%b" + dayjs: "MMM" + +# categories page +categories: + category_measure: + singular: category + plural: categories + post_measure: + singular: post + plural: posts diff --git a/_data/locales/es-ES.yml b/_data/locales/es-ES.yml new file mode 100644 index 0000000..5529230 --- /dev/null +++ b/_data/locales/es-ES.yml @@ -0,0 +1,77 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Entrada + category: Categoría + tag: Etiqueta + +# The tabs of sidebar +tabs: + # format: : + home: Inicio + categories: Categorías + tags: Etiquetas + archives: Archivo + about: Acerca de + +# the text displayed in the search bar & search results +search: + hint: Buscar + cancel: Cancelar + no_results: ¡Oops! No se encuentran resultados. + +panel: + lastmod: Actualizado recientemente + trending_tags: Etiquetas populares + toc: Contenido + +copyright: + # Shown at the bottom of the post + license: + template: Esta entrada está licenciada bajo :LICENSE_NAME por el autor. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Algunos derechos reservados. + verbose: >- + Salvo que se indique explícitamente, las entradas de este blog están licenciadas + bajo la Creative Commons Attribution 4.0 International (CC BY 4.0) License por el autor. + +meta: Hecho con :PLATFORM usando el tema :THEME + +not_found: + statment: Lo sentimos, hemos perdido esa URL o apunta a algo que no existe. + +notification: + update_found: Hay una nueva versión de contenido disponible. + update: Actualizar + +# ----- Posts related labels ----- + +post: + written_by: Por + posted: Publicado + updated: Actualizado + words: palabras + pageview_measure: visitas + read_time: + unit: min + prompt: " de lectura" + relate_posts: Lecturas adicionales + share: Compartir + button: + next: Nuevo + previous: Anterior + copy_code: + succeed: ¡Copiado! + share_link: + title: Copiar enlace + succeed: ¡Enlace copiado! + +# categories page +categories: + category_measure: categorias + post_measure: entradas diff --git a/_data/locales/fi-FI.yml b/_data/locales/fi-FI.yml new file mode 100644 index 0000000..c817d2b --- /dev/null +++ b/_data/locales/fi-FI.yml @@ -0,0 +1,90 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Julkaisu + category: Kateogoria + tag: Tagi + +# The tabs of sidebar +tabs: + # format: : + home: Koti + categories: Kateogoriat + tags: Tagit + archives: Arkistot + about: Minusta + +# the text displayed in the search bar & search results +search: + hint: etsi + cancel: Peruuta + no_results: Hups! Ei tuloksia. + +panel: + lastmod: Viimeksi päivitetty + trending_tags: Trendaavat tagit + toc: Sisältö + +copyright: + # Shown at the bottom of the post + license: + template: Tämä julkaisu on lisenssoitu :LICENSE_NAME julkaisijan toimesta. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Jotkut oikeudet pidätetään. + verbose: >- + Paitsi jos erikseen mainitaan on kaikki sisältö Creative Commons Attribution 4.0 International (CC BY 4.0) Lisensoitu kirjoittajan toimesta. + +meta: Käytetään :PLATFORM iä Teema :THEME + +not_found: + statment: Valitettavasti tällä URL-osoitteella ei ole saatavilla sisältöä. + +notification: + update_found: Uusi versio sisällöstä on saatavilla. + update: Päivitä + +# ----- Posts related labels ----- + +post: + written_by: Kirjoittaja + posted: Julkaistu + updated: Päivitetty + words: sanaa + pageview_measure: katselukertoja + read_time: + unit: minuuttia + prompt: lukea + relate_posts: Jatka lukemista + share: Jaa + button: + next: Uudempi + previous: Vanhempi + copy_code: + succeed: Kopiotu! + share_link: + title: Kopioi linkki + succeed: Linkki kopioitu onnistuneesti! + +# Date time format. +# See: , +df: + post: + strftime: "%b %e, %Y" + dayjs: "ll" + archives: + strftime: "%b" + dayjs: "MMM" + +# categories page +categories: + category_measure: + singular: kategoria + plural: kategoriat + post_measure: + singular: julkaisu + plural: julkaisut diff --git a/_data/locales/fr-FR.yml b/_data/locales/fr-FR.yml new file mode 100644 index 0000000..72b034d --- /dev/null +++ b/_data/locales/fr-FR.yml @@ -0,0 +1,77 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Post + category: Catégorie + tag: Tag + +# The tabs of sidebar +tabs: + # format: : + home: Accueil + categories: Catégories + tags: Tags + archives: Archives + about: A propos de + +# the text displayed in the search bar & search results +search: + hint: recherche + cancel: Annuler + no_results: Oups ! Aucun résultat trouvé. + +panel: + lastmod: Récemment mis à jour + trending_tags: Tags tendance + toc: Contenu + +copyright: + # Shown at the bottom of the post + license: + template: Cet article est sous licence :LICENSE_NAME par l'auteur. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Certains droits réservés. + verbose: >- + Sauf mention contraire, les articles de ce site sont publiés sous licence + sous la licence Creative Commons Attribution 4.0 International (CC BY 4.0) par l'auteur. + +meta: Propulsé par :PLATFORM avec le thème :THEME + +not_found: + statment: Désolé, nous avons égaré cette URL ou elle pointe vers quelque chose qui n'existe pas. + +notification: + update_found: Une nouvelle version du contenu est disponible. + update: Mise à jour + +# ----- Posts related labels ----- + +post: + written_by: Par + posted: Posté + updated: Mis à jour + words: mots + pageview_measure: vues + read_time: + unit: min + prompt: lire + relate_posts: Autres lectures + share: Partager + button: + next: Plus récent + previous: Plus ancien + copy_code: + succeed: Copié ! + share_link: + title: Copier le lien + succeed: Lien copié avec succès ! + +# categories page +categories: + category_measure: catégories + post_measure: posts diff --git a/_data/locales/hu-HU.yml b/_data/locales/hu-HU.yml new file mode 100644 index 0000000..b09f2cd --- /dev/null +++ b/_data/locales/hu-HU.yml @@ -0,0 +1,79 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Bejegyzés + category: Kategória + tag: Címke + +# The tabs of sidebar +tabs: + # format: : + home: Kezdőlap + categories: Kategóriák + tags: Címkék + archives: Archívum + about: Rólam + +# the text displayed in the search bar & search results +search: + hint: keresés + cancel: Mégse + no_results: Oops! Nincs találat a keresésre. + +panel: + lastmod: Legutóbb frissítve + trending_tags: Népszerű Címkék + toc: Tartalom + links: Blog linkek + +copyright: + # Shown at the bottom of the post + license: + template: A bejegyzés :LICENSE_NAME licenccel rendelkezik. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Néhány jog fenntartva. + verbose: >- + Az oldalon található tartalmak + Creative Commons Attribution 4.0 International (CC BY 4.0) licenccel rendelkeznek, + hacsak másképp nincs jelezve. + +meta: Készítve :PLATFORM motorral :THEME témával + +not_found: + statment: Sajnáljuk, az URL-t rosszul helyeztük el, vagy valami nem létezőre mutat. + +notification: + update_found: Elérhető a tartalom új verziója. + update: Frissítés + +# ----- Posts related labels ----- + +post: + written_by: Szerző + posted: Létrehozva + updated: Frissítve + words: szó + pageview_measure: látogató + read_time: + unit: perc + prompt: elolvasni + relate_posts: További olvasnivaló + share: Megosztás + button: + next: Újabb + previous: Régebbi + copy_code: + succeed: Másolva! + share_link: + title: Link másolása + succeed: Link sikeresen másolva! + +# categories page +categories: + category_measure: kategória + post_measure: bejegyzés diff --git a/_data/locales/id-ID.yml b/_data/locales/id-ID.yml new file mode 100644 index 0000000..29ad156 --- /dev/null +++ b/_data/locales/id-ID.yml @@ -0,0 +1,77 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Postingan + category: Kategori + tag: Tagar + +# The tabs of sidebar +tabs: + # format: : + home: Beranda + categories: Kategori + tags: Tagar + archives: Arsip + about: Tentang + +# the text displayed in the search bar & search results +search: + hint: Cari + cancel: Batal + no_results: Ups! Tidak ada hasil yang ditemukan. + +panel: + lastmod: Postingan Terbaru + trending_tags: Tagar Terpopuler + toc: Konten + +copyright: + # Shown at the bottom of the post + license: + template: Postingan ini dilisensikan di bawah :LICENSE_NAME oleh penulis. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Sebagian konten dilindungi. + verbose: >- + Kecuali jika dinyatakan, Postingan blog di situs ini dilisensikan + di bawah Lisensi Creative Commons Attribution 4.0 International (CC BY 4.0) oleh penulis. + +meta: Didukung oleh :PLATFORM dengan tema :THEME + +not_found: + statment: Maaf, kami gagal menemukan URL itu atau memang mengarah ke sesuatu yang tidak ada. + +notification: + update_found: Versi konten baru tersedia. + update: Perbarui + +# ----- Posts related labels ----- + +post: + written_by: Oleh + posted: Diterbitkan + updated: Diperbarui + words: kata + pageview_measure: dilihat + read_time: + unit: menit + prompt: baca + relate_posts: Postingan Lainya + share: Bagikan + button: + next: Terbaru + previous: Terlama + copy_code: + succeed: Disalin! + share_link: + title: Salin tautan + succeed: Tautan berhasil disalin! + +# categories page +categories: + category_measure: kategori + post_measure: Postingan diff --git a/_data/locales/it-IT.yml b/_data/locales/it-IT.yml new file mode 100644 index 0000000..cf7b691 --- /dev/null +++ b/_data/locales/it-IT.yml @@ -0,0 +1,90 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Post + category: Categoria + tag: Tag + +# The tabs of sidebar +tabs: + # format: : + home: Pagina principale + categories: Categorie + tags: Tags + archives: Archivio + about: Informazioni + +# the text displayed in the search bar & search results +search: + hint: ricerca + cancel: Cancella + no_results: Oops! La ricerca non ha fornito risultati. + +panel: + lastmod: Aggiornati recentemente + trending_tags: Tags più cliccati + toc: Contenuti + +copyright: + # Shown at the bottom of the post + license: + template: Questo post è sotto licenza :LICENSE_NAME a nome dell'autore. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Alcuni diritti riservati. + verbose: >- + Eccetto quando esplicitamente menzionato, i post di questo blog sono da ritenersi sotto + i termini di licenza Creative Commons Attribution 4.0 International (CC BY 4.0). + +meta: Servizio offerto da :PLATFORM con tema :THEME +not_found: + statment: Ci scusiamo, non è stato possibile trovare l'URL in questione. Potrebbe puntare ad una pagina non esistente. + +notification: + update_found: Nuova versione del contenuto disponibile. + update: Aggiornamento + +# ----- Posts related labels ----- + +post: + written_by: Da + posted: Postato + updated: Aggiornato + words: parole + pageview_measure: visioni + read_time: + unit: min + prompt: lettura + relate_posts: Continua a leggere + share: Condividi + button: + next: Più recenti + previous: Meno recenti + copy_code: + succeed: Copiato! + share_link: + title: Copia link + succeed: Link copiato con successo! + +# Date time format. +# See: , +df: + post: + strftime: "%b %e, %Y" + dayjs: "ll" + archives: + strftime: "%b" + dayjs: "MMM" + +# categories page +categories: + category_measure: + singular: categoria + plural: categorie + post_measure: + singular: post + plural: posts diff --git a/_data/locales/ko-KR.yml b/_data/locales/ko-KR.yml new file mode 100644 index 0000000..4dd221b --- /dev/null +++ b/_data/locales/ko-KR.yml @@ -0,0 +1,84 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: 포스트 + category: 카테고리 + tag: 태그 + +# The tabs of sidebar +tabs: + # format: : + home: 홈 + categories: 카테고리 + tags: 태그 + archives: 아카이브 + about: 정보 + +# the text displayed in the search bar & search results +search: + hint: 검색 + cancel: 취소 + no_results: 검색 결과가 없습니다. + +panel: + lastmod: 최근 업데이트 + trending_tags: 인기 태그 + toc: 바로가기 + +copyright: + # Shown at the bottom of the post + license: + template: 이 기사는 저작권자의 :LICENSE_NAME 라이센스를 따릅니다. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: 일부 권리 보유 + verbose: >- + 명시되지 않는 한 이 사이트의 블로그 게시물은 작성자의 + Creative Commons Attribution 4.0 International(CC BY 4.0) 라이선스에 따라 사용이 허가되었습니다. + +meta: Powered by :PLATFORM with :THEME theme + +not_found: + statment: 해당 URL은 존재하지 않습니다. + +notification: + update_found: 새 버전의 콘텐츠를 사용할 수 있습니다. + update: 업데이트 + +# ----- Posts related labels ----- + +post: + written_by: By + posted: 게시 + updated: 업데이트 + words: 단어 + pageview_measure: 조회 + read_time: + unit: 분 + prompt: 읽는 시간 + relate_posts: 관련된 글 + share: 공유하기 + button: + next: 다음 글 + previous: 이전 글 + copy_code: + succeed: 복사되었습니다! + share_link: + title: 링크 복사하기 + succeed: 링크가 복사되었습니다! + +# Date time format. +# See: , +df: + post: + strftime: "%Y/%m/%d" + dayjs: "YYYY/MM/DD" + +# categories page +categories: + category_measure: 카테고리 + post_measure: 포스트 diff --git a/_data/locales/my-MM.yml b/_data/locales/my-MM.yml new file mode 100644 index 0000000..98848d5 --- /dev/null +++ b/_data/locales/my-MM.yml @@ -0,0 +1,77 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: ပို့စ် + category: ကဏ္ဍ + tag: နာမ(တက်ဂ်) + +# The tabs of sidebar +tabs: + # format: : + home: အဓိကစာမျက်နှာ + categories: ကဏ္ဍများ + tags: နာမ(တက်ဂ်)များ + archives: မှတ်တမ်း​တိုက် + about: အကြောင်းအရာ + +# the text displayed in the search bar & search results +search: + hint: ရှာဖွေမည် + cancel: ဖျက်သိမ်းမည် + no_results: အိုး! ဘာမှမရှိပါ + +panel: + lastmod: မကြာသေးမီကမွမ်းမံထားသည် + trending_tags: ခေတ်စားနေသည့်တက်ဂ်များ + toc: အကြောင်းအရာများ + +copyright: + # Shown at the bottom of the post + license: + template: ဤပို့စ်သည်စာရေးသူ၏ :LICENSE_NAME လိုင်စင်ရထားသည်။ + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: မူပိုင်ခွင့်အချို့ကို လက်ဝယ်ထားသည်။ + verbose: >- + အခြားမှတ်သားထားချက်များမှလွဲ၍ ဤဆိုက်ရှိ ဘလော့ဂ်ပို့စ်များသည် စာရေးသူ၏ + Creative Commons Attribution 4.0 International (CC BY 4.0) အောက်တွင် လိုင်စင်ရထားပါသည်။ + +meta: Powered by :PLATFORM with :THEME theme + +not_found: + statment: ဝမ်းနည်းပါသည်၊ ကျွန်ုပ်တို့သည် အဆိုပါ URL ကို မှားယွင်းစွာ နေရာချထားခြင်း သို့မဟုတ် ၎င်းသည် မရှိသောအရာကို ညွှန်ပြနေပါသည်။ + +notification: + update_found: အကြောင်းအရာဗားရှင်းအသစ်ကို ရနိုင်ပါပြီ။ + update: အပ်ဒိတ် + +# ----- Posts related labels ----- + +post: + written_by: ကရေးသားခဲ့သည်။ + posted: တင်ထားခဲ့သည်။ + updated: မွမ်းမံထားခဲ့သည်။ + words: စကားလုံးများ + pageview_measure: အမြင်များ + read_time: + unit: မိနစ် + prompt: ဖတ်ပါမည် + relate_posts: နောက်ထပ်ဖတ်ရန် + share: မျှဝေရန် + button: + next: အသစ်များ + previous: အဟောင်းများ + copy_code: + succeed: ကူးယူလိုက်ပြီ။ + share_link: + title: လင့်ခ်ကို ကူးယူရန် + succeed: လင့်ခ်ကို ကူးယူလိုက်ပြီ။ + +# categories page +categories: + category_measure: ကဏ္ဍများ + post_measure: ပို့စ်များ diff --git a/_data/locales/pt-BR.yml b/_data/locales/pt-BR.yml new file mode 100644 index 0000000..4cef833 --- /dev/null +++ b/_data/locales/pt-BR.yml @@ -0,0 +1,77 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Post + category: Categoria + tag: Tag + +# The tabs of sidebar +tabs: + # format: : + home: Home + categories: Categorias + tags: Tags + archives: Arquivos + about: Sobre + +# the text displayed in the search bar & search results +search: + hint: Buscar + cancel: Cancelar + no_results: Oops! Nenhum resultado encontrado. + +panel: + lastmod: Atualizados recentemente + trending_tags: Trending Tags + toc: Conteúdo + +copyright: + # Shown at the bottom of the post + license: + template: Esta postagem está licenciada sob :LICENSE_NAME pelo autor. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Alguns direitos reservados. + verbose: >- + Exceto onde indicado de outra forma, as postagens do blog neste site são licenciadas sob a + Creative Commons Attribution 4.0 International (CC BY 4.0) License pelo autor. + +meta: Feito com :PLATFORM usando o tema :THEME + +not_found: + statment: Desculpe, a página não foi encontrada. + +notification: + update_found: Uma nova versão do conteúdo está disponível. + update: atualização + +# ----- Posts related labels ----- + +post: + written_by: Por + posted: Postado em + updated: Atualizado + words: palavras + pageview_measure: visualizações + read_time: + unit: min + prompt: " de leitura" + relate_posts: Leia também + share: Compartilhar + button: + next: Próximo + previous: Anterior + copy_code: + succeed: Copiado! + share_link: + title: Copie o link + succeed: Link copiado com sucesso! + +# categories page +categories: + category_measure: categorias + post_measure: posts diff --git a/_data/locales/ru-RU.yml b/_data/locales/ru-RU.yml new file mode 100644 index 0000000..185407c --- /dev/null +++ b/_data/locales/ru-RU.yml @@ -0,0 +1,87 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Пост + category: Категория + tag: Тег + +# The tabs of sidebar +tabs: + # format: : + home: Главная + categories: Категории + tags: Теги + archives: Архив + about: О сайте + +# the text displayed in the search bar & search results +search: + hint: поиск + cancel: Отмена + no_results: Упс! Ничего не найдено. + +panel: + lastmod: Недавно обновлено + trending_tags: Популярные теги + toc: Содержание + +copyright: + # Shown at the bottom of the post + license: + template: Авторский пост защищен лицензией :LICENSE_NAME. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Некоторые права защищены. + verbose: >- + Если не указано иное, авторские посты на этом сайте защищены лицензией Creative Commons Attribution 4.0 International (CC BY 4.0). + +meta: Использует тему :THEME для :PLATFORM + +not_found: + statment: Извините, мы перепутали URL-адрес или он указывает на что-то несуществующее. + +notification: + update_found: Доступна новая версия контента. + update: Обновить + +# ----- Posts related labels ----- + +post: + written_by: Автор + posted: Опубликовано + updated: Обновлено + words: слов + pageview_measure: просмотров + read_time: + unit: мин. + prompt: чтения + relate_posts: Похожие посты + share: Поделиться + button: + next: Следующий пост + previous: Предыдущий пост + copy_code: + succeed: Скопировано! + share_link: + title: Скопировать ссылку + succeed: Ссылка успешно скопирована! + +# Date time format. +# See: , +df: + post: + strftime: "%d.%m.%Y" + dayjs: "DD.MM.YYYY" + +# categories page +categories: + category_measure: + singular: категория + plural: категории + post_measure: + singular: пост + plural: посты diff --git a/_data/locales/sl-SI.yml b/_data/locales/sl-SI.yml new file mode 100644 index 0000000..7ab18b1 --- /dev/null +++ b/_data/locales/sl-SI.yml @@ -0,0 +1,91 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Objava #Post + category: Kategorija #Category + tag: Oznaka #Tag + +# The tabs of sidebar +tabs: + # format: : + home: Domov #Home + categories: Kategorije #Categories + tags: Oznake #Tags + archives: Arhiv #Archives + about: O meni #About + +# the text displayed in the search bar & search results +search: + hint: išči #search + cancel: Prekliči #Cancel + no_results: Ups! Vsebina ni bila najdena #Oops! No results found. + +panel: + lastmod: Nedavno Posodobljeno #Recently Updated + trending_tags: Priljubljene Oznake #Trending Tags + toc: Vsebina #Contents + +copyright: + # Shown at the bottom of the post + license: + template: Ta objava je licencirana pod :LICENCE_NAME s strani avtorja. #This post is licensed under :LICENSE_NAME by the author. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Nekatere pravice pridržane. #Some rights reserved. + verbose: >- + Razen kjer navedeno drugače, vse objave spletnega dnevnika so licencirane + pod Creative Commons Attribution 4.0 International (CC BY 4.0) s strani avtorja. + +meta: Uporabljena :PLATFORM tema :THEME #Using the :PLATFORM theme :THEME + +not_found: + statment: Oprostite, hiperpovezava je neustrezna ali vsebina ne obstajata. #Sorry, we've misplaced that URL or it's pointing to something that doesn't exist. + +notification: + update_found: Novejša različica vsebine je na voljo. #A new version of content is available. + update: Posodobi #Update + +# ----- Posts related labels ----- + +post: + written_by: Od #By + posted: Objavljeno #Posted + updated: Posodobljeno #Updated + words: besede #words + pageview_measure: ogledi #views + read_time: + unit: min + prompt: beri #read + relate_posts: Nadaljnje branje #Further Reading + share: Deli #Share + button: + next: Novejše #Newer + previous: Starejše #Older + copy_code: + succeed: Kopirano! #Copied! + share_link: + title: Kopiraj povezavo #Copy link + succeed: Povezava uspešno kopirana! #Link copied successfully! + +# Date time format. +# See: , +df: + post: + strftime: "%e %b, %Y" + dayjs: "ll" + archives: + strftime: "%b" + dayjs: "MMM" + +# categories page +categories: + category_measure: + singular: kategorija #category + plural: kategorije #categories + post_measure: + singular: objava #post + plural: objave #posts diff --git a/_data/locales/sv-SE.yml b/_data/locales/sv-SE.yml new file mode 100644 index 0000000..7ec2ee2 --- /dev/null +++ b/_data/locales/sv-SE.yml @@ -0,0 +1,91 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Inlägg #Post + category: Kategori #Category + tag: Tagga #Tag + +# The tabs of sidebar +tabs: + # format: : + home: Hem #Home + categories: Kategorier #Categories + tags: Taggar #Tags + archives: Arkiv #Archives + about: Om #About + +# the text displayed in the search bar & search results +search: + hint: sök + cancel: Avbryt + no_results: Hoppsan! Hittade inga sökträffar. + +panel: + lastmod: Senast uppdaterad + trending_tags: Trendande taggar + toc: Innehåll + +copyright: + # Shown at the bottom of the post + license: + template: Den här posten är publicerad under licensen :LICENSE_NAME av författaren. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Vissa rättigheter är reserverade. + verbose: >- + Om inte annat anges är blogginläggen på denna webbplats licensierade + under Creative Commons Attribution 4.0 International (CC BY 4.0) av författaren. + +meta: Byggd med :PLATFORM och temat :THEME + +not_found: + statment: Ursäkta, vi har tappat bort den här webbadressen eller så pekar den på något som inte längre finns. + +notification: + update_found: Det finns en ny version av innehållet. + update: Uppdatera sidan + +# ----- Posts related labels ----- + +post: + written_by: Av + posted: Postad + updated: Uppdaterad + words: ord + pageview_measure: visningar + read_time: + unit: min + prompt: läsning + relate_posts: Mer läsning + share: Dela + button: + next: Nyare + previous: Äldre + copy_code: + succeed: Kopierat! + share_link: + title: Kopiera länk + succeed: Länken har kopierats! + +# Date time format. +# See: , +df: + post: + strftime: "%b %e, %Y" + dayjs: "ll" + archives: + strftime: "%b" + dayjs: "MMM" + +# categories page +categories: + category_measure: + singular: kategori + plural: kategorier + post_measure: + singular: inlägg + plural: inlägg diff --git a/_data/locales/th.yml b/_data/locales/th.yml new file mode 100644 index 0000000..22cb00a --- /dev/null +++ b/_data/locales/th.yml @@ -0,0 +1,91 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: โพสต์ + category: หมวดหมู่ + tag: แท็ก + +# The tabs of sidebar +tabs: + # format: : + home: หน้าแรก + categories: หมวดหมู่ + tags: แท็ก + archives: คลังเก็บ + about: เกี่ยวกับ + +# the text displayed in the search bar & search results +search: + hint: ค้นหา + cancel: ยกเลิก + no_results: โอ๊ะ! ไม่พบผลลัพธ์ + +panel: + lastmod: อัปเดตล่าสุด + trending_tags: แท็กยอดนิยม + toc: เนื้อหา + +copyright: + # Shown at the bottom of the post + license: + template: โพสต์นี้อยู่ภายใต้การอนุญาต :LICENSE_NAME โดยผู้เขียน + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: สงวนลิขสิทธิ์เป็นบางส่วน + verbose: >- + เว้นแต่ว่าจะระบุเป็นอย่างอื่น โพสต์บนเว็บไซต์นี้อยู่ภายใต้ + สัญญาอนุญาตครีเอทีฟคอมมอนส์แบบ 4.0 นานาชาติ (CC BY 4.0) โดยผู้เขียน + +meta: กำลังใช้ธีมของ :PLATFORM ชื่อ :THEME + +not_found: + statment: ขออภัย เราวาง URL นั้นไว้ผิดที่ หรือมันชี้ไปยังสิ่งที่ไม่มีอยู่ + +notification: + update_found: มีเวอร์ชันใหม่ของเนื้อหา + update: อัปเดต + +# ----- Posts related labels ----- + +post: + written_by: โดย + posted: โพสต์เมื่อ + updated: อัปเดตเมื่อ + words: คำ + pageview_measure: ครั้ง + read_time: + unit: นาที + prompt: อ่าน + relate_posts: อ่านต่อ + share: แชร์ + button: + next: ใหม่กว่า + previous: เก่ากว่า + copy_code: + succeed: คัดลอกแล้ว! + share_link: + title: คัดลอกลิงก์ + succeed: คัดลอกลิงก์เรียบร้อยแล้ว! + +# Date time format. +# See: , +df: + post: + strftime: "%b %e, %Y" + dayjs: "ll" + archives: + strftime: "%b" + dayjs: "MMM" + +# categories page +categories: + category_measure: + singular: หมวดหมู่ + plural: หมวดหมู่ + post_measure: + singular: โพสต์ + plural: โพสต์ diff --git a/_data/locales/tr-TR.yml b/_data/locales/tr-TR.yml new file mode 100644 index 0000000..50d8110 --- /dev/null +++ b/_data/locales/tr-TR.yml @@ -0,0 +1,77 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Gönderi + category: Kategori + tag: Etiket + +# The tabs of sidebar +tabs: + # format: : + home: Ana Sayfa + categories: Kategoriler + tags: Etiketler + archives: Arşiv + about: Hakkında + +# the text displayed in the search bar & search results +search: + hint: Ara... + cancel: İptal + no_results: Hop! Öyle bir şey bulamadım. + +panel: + lastmod: Son Güncellenenler + trending_tags: Yükselen Etiketler + toc: İçindekiler + +copyright: + # Shown at the bottom of the post + license: + template: Bu gönderi :LICENSE_NAME lisansı altındadır. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/deed.tr + + # Displayed in the footer + brief: Bazı hakları saklıdır. + verbose: >- + Aksi belirtilmediği sürece, bu sitedeki gönderiler Creative Commons Atıf 4.0 Uluslararası (CC BY 4.0) Lisansı altındadır. + Kısaca sayfa linkini vererek değiştirebilir / paylaşabilirsiniz. + +meta: :PLATFORM ve :THEME teması + +not_found: + statment: Üzgünüz, bu linki yanlış yerleştirdik veya var olmayan bir şeye işaret ediyor. + +notification: + update_found: İçeriğin yeni bir sürümü mevcut. + update: Güncelle + +# ----- Posts related labels ----- + +post: + written_by: Yazan + posted: Gönderim + updated: Güncelleme + words: sözcük + pageview_measure: görüntülenme + read_time: + unit: dakikada + prompt: okunabilir + relate_posts: Benzer Gönderiler + share: Paylaş + button: + next: İleri + previous: Geri + copy_code: + succeed: Kopyalandı. + share_link: + title: Linki kopyala + succeed: Link kopyalandı. + +# categories page +categories: + category_measure: kategori + post_measure: gönderi diff --git a/_data/locales/uk-UA.yml b/_data/locales/uk-UA.yml new file mode 100644 index 0000000..b605073 --- /dev/null +++ b/_data/locales/uk-UA.yml @@ -0,0 +1,77 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Публікація + category: Категорія + tag: Тег + +# The tabs of sidebar +tabs: + # format: : + home: Домашня сторінка + categories: Категорії + tags: Теги + archives: Архів + about: Про сайт + +# the text displayed in the search bar & search results +search: + hint: пошук + cancel: Скасувати + no_results: Ох! Нічого не знайдено. + +panel: + lastmod: Нещодавно оновлено + trending_tags: Популярні теги + toc: Зміст + +copyright: + # Shown at the bottom of the post + license: + template: Публікація захищена ліцензією :LICENSE_NAME. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Деякі права захищено. + verbose: >- + Публікації на сайті захищено ліцензією Creative Commons Attribution 4.0 International (CC BY 4.0), + якщо інше не вказано в тексті. + +meta: Powered by :PLATFORM with :THEME theme + +not_found: + statment: Вибачте, це посилання вказує на ресурс, що не існує. + +notification: + update_found: Доступна нова версія вмісту. + update: Оновлення + +# ----- Posts related labels ----- + +post: + written_by: Автор + posted: Час публікації + updated: Оновлено + words: слів + pageview_measure: переглядів + read_time: + unit: хвилин + prompt: читання + relate_posts: Вас також може зацікавити + share: Поділитися + button: + next: Попередня публікація + previous: Наступна публікація + copy_code: + succeed: Успішно скопійовано! + share_link: + title: Скопіювати посилання + succeed: Посилання успішно скопійовано! + +# categories page +categories: + category_measure: категорії + post_measure: публікації diff --git a/_data/locales/vi-VN.yml b/_data/locales/vi-VN.yml new file mode 100644 index 0000000..617431a --- /dev/null +++ b/_data/locales/vi-VN.yml @@ -0,0 +1,76 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: Bài viết + category: Danh mục + tag: Thẻ + +# The tabs of sidebar +tabs: + # format: : + home: Trang chủ + categories: Các danh mục + tags: Các thẻ + archives: Lưu trữ + about: Giới thiệu + +# the text displayed in the search bar & search results +search: + hint: tìm kiếm + cancel: Hủy + no_results: Không có kết quả tìm kiếm. + +panel: + lastmod: Mới cập nhật + trending_tags: Các thẻ thịnh hành + toc: Mục lục + +copyright: + # Shown at the bottom of the post + license: + template: Bài viết này được cấp phép bởi tác giả theo giấy phép :LICENSE_NAME. + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: Một số quyền được bảo lưu. + verbose: >- + Trừ khi có ghi chú khác, các bài viết đăng trên trang này được cấp phép bởi tác giả theo giấy phép Creative Commons Attribution 4.0 International (CC BY 4.0). + +meta: Trang web này được tạo bởi :PLATFORM với chủ đề :THEME + +not_found: + statment: Xin lỗi, chúng tôi đã đặt nhầm URL hoặc đường dẫn trỏ đến một trang nào đó không tồn tại. + +notification: + update_found: Đã có phiên bản mới của nội dung. + update: Cập nhật + +# ----- Posts related labels ----- + +post: + written_by: Viết bởi + posted: Đăng lúc + updated: Cập nhật lúc + words: từ + pageview_measure: lượt xem + read_time: + unit: phút + prompt: đọc + relate_posts: Bài viết liên quan + share: Chia sẻ + button: + next: Mới hơn + previous: Cũ hơn + copy_code: + succeed: Đã sao chép! + share_link: + title: Sao chép đường dẫn + succeed: Đã sao chép đường dẫn thành công! + +# categories page +categories: + category_measure: danh mục + post_measure: bài viết diff --git a/_data/locales/zh-CN.yml b/_data/locales/zh-CN.yml new file mode 100644 index 0000000..f828134 --- /dev/null +++ b/_data/locales/zh-CN.yml @@ -0,0 +1,83 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: 文章 + category: 分类 + tag: 标签 + +# The tabs of sidebar +tabs: + # format: : + home: 首页 + categories: 分类 + tags: 标签 + archives: 归档 + about: 关于 + +# the text displayed in the search bar & search results +search: + hint: 搜索 + cancel: 取消 + no_results: 搜索结果为空 + +panel: + lastmod: 最近更新 + trending_tags: 热门标签 + toc: 文章内容 + +copyright: + # Shown at the bottom of the post + license: + template: 本文由作者按照 :LICENSE_NAME 进行授权 + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: 保留部分权利。 + verbose: >- + 除非另有说明,本网站上的博客文章均由作者按照知识共享署名 4.0 国际 (CC BY 4.0) 许可协议进行授权。 + +meta: 本站采用 :PLATFORM 主题 :THEME + +not_found: + statment: 抱歉,我们放错了该 URL,或者它指向了不存在的内容。 + +notification: + update_found: 发现新版本的内容。 + update: 更新 + +# ----- Posts related labels ----- + +post: + written_by: 作者 + posted: 发表于 + updated: 更新于 + words: 字 + pageview_measure: 次浏览 + read_time: + unit: 分钟 + prompt: 阅读 + relate_posts: 相关文章 + share: 分享 + button: + next: 下一篇 + previous: 上一篇 + copy_code: + succeed: 已复制! + share_link: + title: 分享链接 + succeed: 链接已复制! + +# Date time format. +# See: , +df: + post: + strftime: "%Y/%m/%d" + dayjs: "YYYY/MM/DD" + +# categories page +categories: + category_measure: 个分类 + post_measure: 篇文章 diff --git a/_data/locales/zh-TW.yml b/_data/locales/zh-TW.yml new file mode 100644 index 0000000..911253b --- /dev/null +++ b/_data/locales/zh-TW.yml @@ -0,0 +1,83 @@ +# The layout text of site + +# ----- Commons label ----- + +layout: + post: 文章 + category: 分類 + tag: 標籤 + +# The tabs of sidebar +tabs: + # format: : + home: 首頁 + categories: 分類 + tags: 標籤 + archives: 封存 + about: 關於 + +# the text displayed in the search bar & search results +search: + hint: 搜尋 + cancel: 取消 + no_results: 沒有搜尋結果 + +panel: + lastmod: 最近更新 + trending_tags: 熱門標籤 + toc: 文章摘要 + +copyright: + # Shown at the bottom of the post + license: + template: 本文章以 :LICENSE_NAME 授權 + name: CC BY 4.0 + link: https://creativecommons.org/licenses/by/4.0/ + + # Displayed in the footer + brief: 保留部份權利。 + verbose: >- + 除非另有說明,否則本網誌的文章均由作者按照姓名標示 4.0 國際 (CC BY 4.0) 授權條款進行授權。 + +meta: 本網站使用 :PLATFORM 產生,採用 :THEME 主題 + +not_found: + statment: 抱歉,您可能正在存取一個已被移動的 URL,或者它從未存在。 + +notification: + update_found: 發現新版本更新。 + update: 更新 + +# ----- Posts related labels ----- + +post: + written_by: 作者 + posted: 發布於 + updated: 更新於 + words: 字 + pageview_measure: 次瀏覽 + read_time: + unit: 分鐘 + prompt: 閱讀 + relate_posts: 相關文章 + share: 分享 + button: + next: 下一篇 + previous: 上一篇 + copy_code: + succeed: 已複製! + share_link: + title: 分享連結 + succeed: 已複製連結! + +# Date time format. +# See: , +df: + post: + strftime: "%Y/%m/%d" + dayjs: "YYYY/MM/DD" + +# categories page +categories: + category_measure: 個分類 + post_measure: 篇文章 diff --git a/_data/origin/basic.yml b/_data/origin/basic.yml new file mode 100644 index 0000000..ed99ea8 --- /dev/null +++ b/_data/origin/basic.yml @@ -0,0 +1,46 @@ +# fonts + +webfonts: /assets/lib/fonts/main.css + +# Libraries + +jquery: + js: /assets/lib/jquery/jquery.min.js + +bootstrap: + css: /assets/lib/bootstrap/bootstrap.min.css + js: /assets/lib/bootstrap/bootstrap.bundle.min.js + +toc: + css: /assets/lib/tocbot/tocbot.min.css + js: /assets/lib/tocbot/tocbot.min.js + +fontawesome: + css: /assets/lib/fontawesome-free/css/all.min.css + +search: + js: /assets/lib/simple-jekyll-search/simple-jekyll-search.min.js + +mermaid: + js: /assets/lib/mermaid/mermaid.min.js + +dayjs: + js: + common: /assets/lib/dayjs/dayjs.min.js + locale: /assets/lib/dayjs/locale/en.min.js + relativeTime: /assets/lib/dayjs/plugin/relativeTime.min.js + localizedFormat: /assets/lib/dayjs/plugin/localizedFormat.min.js + +magnific-popup: + css: /assets/lib/magnific-popup/magnific-popup.css + js: /assets/lib/magnific-popup/jquery.magnific-popup.min.js + +lazy-polyfill: + css: /assets/lib/loading-attribute-polyfill/loading-attribute-polyfill.min.css + js: /assets/lib/loading-attribute-polyfill/loading-attribute-polyfill.umd.min.js + +clipboard: + js: /assets/lib/clipboard/clipboard.min.js + +mathjax: + js: /assets/lib/mathjax/tex-chtml.js diff --git a/_data/origin/cors.yml b/_data/origin/cors.yml new file mode 100644 index 0000000..b6c8674 --- /dev/null +++ b/_data/origin/cors.yml @@ -0,0 +1,59 @@ +# CDNs + +cdns: + # Google Fonts + - url: https://fonts.googleapis.com + - url: https://fonts.gstatic.com + args: crossorigin + - url: https://fonts.googleapis.com + # jsDelivr CDN + - url: https://cdn.jsdelivr.net + # polyfill.io for math (cdnjs.cloudflare.com/polyfill) + - url: https://cdnjs.cloudflare.com + +# fonts + +webfonts: https://fonts.googleapis.com/css2?family=Lato&family=Source+Sans+Pro:wght@400;600;700;900&display=swap + +# Libraries + +jquery: + js: https://cdn.jsdelivr.net/npm/jquery@3.7.1/dist/jquery.min.js + +bootstrap: + css: https://cdn.jsdelivr.net/npm/bootstrap@5.3.2/dist/css/bootstrap.min.css + js: https://cdn.jsdelivr.net/npm/bootstrap@5.3.2/dist/js/bootstrap.bundle.min.js + +toc: + css: https://cdn.jsdelivr.net/npm/tocbot@4.25.0/dist/tocbot.min.css + js: https://cdn.jsdelivr.net/npm/tocbot@4.25.0/dist/tocbot.min.js + +fontawesome: + css: https://cdn.jsdelivr.net/npm/@fortawesome/fontawesome-free@6.5.1/css/all.min.css + +search: + js: https://cdn.jsdelivr.net/npm/simple-jekyll-search@1.10.0/dest/simple-jekyll-search.min.js + +mermaid: + js: https://cdn.jsdelivr.net/npm/mermaid@10.8.0/dist/mermaid.min.js + +dayjs: + js: + common: https://cdn.jsdelivr.net/npm/dayjs@1.11.10/dayjs.min.js + locale: https://cdn.jsdelivr.net/npm/dayjs@1.11.10/locale/:LOCALE.min.js + relativeTime: https://cdn.jsdelivr.net/npm/dayjs@1.11.10/plugin/relativeTime.min.js + localizedFormat: https://cdn.jsdelivr.net/npm/dayjs@1.11.10/plugin/localizedFormat.min.js + +magnific-popup: + css: https://cdn.jsdelivr.net/npm/magnific-popup@1.1.0/dist/magnific-popup.min.css + js: https://cdn.jsdelivr.net/npm/magnific-popup@1.1.0/dist/jquery.magnific-popup.min.js + +lazy-polyfill: + css: https://cdn.jsdelivr.net/npm/loading-attribute-polyfill@2.1.1/dist/loading-attribute-polyfill.min.css + js: https://cdn.jsdelivr.net/npm/loading-attribute-polyfill@2.1.1/dist/loading-attribute-polyfill.umd.min.js + +clipboard: + js: https://cdn.jsdelivr.net/npm/clipboard@2.0.11/dist/clipboard.min.js + +mathjax: + js: https://cdn.jsdelivr.net/npm/mathjax@3.2.2/es5/tex-chtml.js diff --git a/_data/share.yml b/_data/share.yml index 3518801..c04eade 100644 --- a/_data/share.yml +++ b/_data/share.yml @@ -22,7 +22,7 @@ platforms: # - type: Weibo # icon: "fab fa-weibo" - # link: "https://service.weibo.com/share/share.php?title=TITLE&url=URL" + # link: "http://service.weibo.com/share/share.php?title=TITLE&url=URL" # # - type: Mastodon # icon: "fa-brands fa-mastodon" diff --git a/_includes/analytics/cloudflare.html b/_includes/analytics/cloudflare.html new file mode 100644 index 0000000..1eeb1a9 --- /dev/null +++ b/_includes/analytics/cloudflare.html @@ -0,0 +1,7 @@ + + + diff --git a/_includes/analytics/goatcounter.html b/_includes/analytics/goatcounter.html new file mode 100644 index 0000000..3867fdb --- /dev/null +++ b/_includes/analytics/goatcounter.html @@ -0,0 +1,6 @@ + + diff --git a/_includes/analytics/google.html b/_includes/analytics/google.html new file mode 100644 index 0000000..d0aac65 --- /dev/null +++ b/_includes/analytics/google.html @@ -0,0 +1,13 @@ + + + diff --git a/_includes/analytics/matomo.html b/_includes/analytics/matomo.html new file mode 100644 index 0000000..72b2c46 --- /dev/null +++ b/_includes/analytics/matomo.html @@ -0,0 +1,14 @@ + + + diff --git a/_includes/analytics/umami.html b/_includes/analytics/umami.html new file mode 100644 index 0000000..bfcb1d0 --- /dev/null +++ b/_includes/analytics/umami.html @@ -0,0 +1,6 @@ + + diff --git a/_includes/comments.html b/_includes/comments.html new file mode 100644 index 0000000..fef135f --- /dev/null +++ b/_includes/comments.html @@ -0,0 +1,5 @@ + +{% if page.comments and site.comments.provider %} + {% capture path %}comments/{{ site.comments.provider }}.html{% endcapture %} + {% include {{ path }} %} +{% endif %} diff --git a/_includes/comments/disqus.html b/_includes/comments/disqus.html new file mode 100644 index 0000000..2b889a4 --- /dev/null +++ b/_includes/comments/disqus.html @@ -0,0 +1,50 @@ + + +
+

Comments powered by Disqus.

+
+ + diff --git a/_includes/comments/giscus.html b/_includes/comments/giscus.html new file mode 100644 index 0000000..f9becfe --- /dev/null +++ b/_includes/comments/giscus.html @@ -0,0 +1,71 @@ + + diff --git a/_includes/comments/utterances.html b/_includes/comments/utterances.html new file mode 100644 index 0000000..5dd78ed --- /dev/null +++ b/_includes/comments/utterances.html @@ -0,0 +1,49 @@ + + + + diff --git a/_includes/datetime.html b/_includes/datetime.html new file mode 100644 index 0000000..9f954b6 --- /dev/null +++ b/_includes/datetime.html @@ -0,0 +1,20 @@ + + +{% assign df_strftime = site.data.locales[include.lang].df.post.strftime | default: '%d/%m/%Y' %} +{% assign df_dayjs = site.data.locales[include.lang].df.post.dayjs | default: 'DD/MM/YYYY' %} + + diff --git a/_includes/embed/audio.html b/_includes/embed/audio.html new file mode 100644 index 0000000..cf928a7 --- /dev/null +++ b/_includes/embed/audio.html @@ -0,0 +1,35 @@ +{% assign src = include.src | strip %} +{% assign title = include.title | strip %} +{% assign types = include.types | default: '' | strip | split: '|' %} + +{% unless src contains '://' %} + {%- capture src -%} + {% include media-url.html src=src subpath=page.media_subpath %} + {%- endcapture -%} +{% endunless %} + +

+ + {% if title %} + {{ title }} + {% endif %} +

diff --git a/_includes/embed/bilibili.html b/_includes/embed/bilibili.html new file mode 100644 index 0000000..0aa5552 --- /dev/null +++ b/_includes/embed/bilibili.html @@ -0,0 +1,9 @@ + diff --git a/_includes/embed/twitch.html b/_includes/embed/twitch.html new file mode 100644 index 0000000..ed5ec83 --- /dev/null +++ b/_includes/embed/twitch.html @@ -0,0 +1,8 @@ + diff --git a/_includes/embed/video.html b/_includes/embed/video.html new file mode 100644 index 0000000..9b6918f --- /dev/null +++ b/_includes/embed/video.html @@ -0,0 +1,59 @@ +{% assign video_url = include.src %} +{% assign title = include.title %} +{% assign poster_url = include.poster %} +{% assign types = include.types | default: '' | strip | split: '|' %} + +{% unless video_url contains '://' %} + {%- capture video_url -%} + {% include media-url.html src=video_url subpath=page.media_subpath %} + {%- endcapture -%} +{% endunless %} + +{% if poster_url %} + {% unless poster_url contains '://' %} + {%- capture poster_url -%} + {% include media-url.html src=poster_url subpath=page.media_subpath %} + {%- endcapture -%} + {% endunless %} + {% assign poster = 'poster="' | append: poster_url | append: '"' %} +{% endif %} + +{% assign attributes = 'controls' %} + +{% if include.autoplay %} + {% assign attributes = attributes | append: ' ' | append: 'autoplay' %} +{% endif %} + +{% if include.loop %} + {% assign attributes = attributes | append: ' ' | append: 'loop' %} +{% endif %} + +{% if include.muted %} + {% assign attributes = attributes | append: ' ' | append: 'muted' %} +{% endif %} + +

+ + {% if title %} + {{ title }} + {% endif %} +

diff --git a/_includes/embed/youtube.html b/_includes/embed/youtube.html new file mode 100644 index 0000000..8f08002 --- /dev/null +++ b/_includes/embed/youtube.html @@ -0,0 +1,9 @@ + diff --git a/_includes/favicons.html b/_includes/favicons.html index fbc4087..957c933 100644 --- a/_includes/favicons.html +++ b/_includes/favicons.html @@ -16,4 +16,4 @@ - \ No newline at end of file + diff --git a/_includes/footer.html b/_includes/footer.html index 470a416..74971bc 100644 --- a/_includes/footer.html +++ b/_includes/footer.html @@ -8,9 +8,15 @@ " >

- {{ '©' }} + {{- '©' }} - {{ site.social.name }}. + + {% if site.social.links %} + {{ site.social.name }}. + {% else %} + {{ site.social.name }}. + {% endif %} + {% if site.data.locales[include.lang].copyright.brief %} -

Kozenet Pro

diff --git a/_includes/goatcounter.html b/_includes/goatcounter.html new file mode 100644 index 0000000..4d21d21 --- /dev/null +++ b/_includes/goatcounter.html @@ -0,0 +1,8 @@ + + + + diff --git a/_includes/google-analytics.html b/_includes/google-analytics.html new file mode 100644 index 0000000..e5e5119 --- /dev/null +++ b/_includes/google-analytics.html @@ -0,0 +1,14 @@ + + + + diff --git a/_includes/head.html b/_includes/head.html new file mode 100644 index 0000000..fd260c0 --- /dev/null +++ b/_includes/head.html @@ -0,0 +1,107 @@ + + + + + + + + + {%- capture seo_tags -%} + {% seo title=false %} + {%- endcapture -%} + + + + {% if page.image %} + {% assign src = page.image.path | default: page.image %} + + {% unless src contains '://' %} + {%- capture img_url -%} + {% include media-url.html src=src subpath=page.media_subpath absolute=true %} + {%- endcapture -%} + + {%- capture old_url -%}{{ src | absolute_url }}{%- endcapture -%} + {%- capture new_url -%}{{ img_url }}{%- endcapture -%} + + {% assign seo_tags = seo_tags | replace: old_url, new_url %} + {% endunless %} + + {% elsif site.social_preview_image %} + {%- capture img_url -%} + {% include media-url.html src=site.social_preview_image absolute=true %} + {%- endcapture -%} + + {%- capture og_image -%} + + {%- endcapture -%} + + {%- capture twitter_image -%} + + + {%- endcapture -%} + + {% assign old_meta_clip = '' %} + {% assign new_meta_clip = og_image | append: twitter_image %} + {% assign seo_tags = seo_tags | replace: old_meta_clip, new_meta_clip %} + {% endif %} + + {{ seo_tags }} + + + {%- unless page.layout == 'home' -%} + {{ page.title | append: ' | ' }} + {%- endunless -%} + {{ site.title }} + + + {% include_cached favicons.html %} + + + {% unless site.assets.self_host.enabled %} + {% for hint in site.data.origin.cors.resource_hints %} + {% for link in hint.links %} + + {% endfor %} + {% endfor %} + {% endunless %} + + + {% unless jekyll.environment == 'production' %} + + {% endunless %} + + + + + + + + + + + + + {% if site.toc and page.toc %} + + {% endif %} + + {% if page.layout == 'post' or page.layout == 'page' or page.layout == 'home' %} + + {% endif %} + + {% if page.layout == 'page' or page.layout == 'post' %} + + + {% endif %} + + + + {% unless site.theme_mode %} + {% include mode-toggle.html %} + {% endunless %} + + {% include metadata-hook.html %} + diff --git a/_includes/img-url.html b/_includes/img-url.html new file mode 100644 index 0000000..2f8d401 --- /dev/null +++ b/_includes/img-url.html @@ -0,0 +1,39 @@ +{%- comment -%} + Generate image final URL based on `site.img_cdn`, `page.img_path` + + Arguments: + src - required, basic image path + img_path - optional, relative path of image + absolute - optional, boolean, if true, generate absolute URL + + Return: + image URL +{%- endcomment -%} + +{% assign url = include.src %} + +{%- if url -%} + {% unless url contains ':' %} + {%- comment -%} CND URL {%- endcomment -%} + {% assign prefix = site.img_cdn | default: '' %} + + {%- comment -%} Add page image path prefix {%- endcomment -%} + {% assign url = include.img_path | default: '' | append: '/' | append: url %} + + {% assign url = prefix + | append: '/' + | append: url + | replace: '///', '/' + | replace: '//', '/' + | replace: ':', ':/' + %} + + {% if include.absolute %} + {% assign url = site.url | append: site.baseurl | append: url %} + {% else %} + {% assign url = site.baseurl | append: url %} + {% endif %} + {% endunless %} +{%- endif -%} + +{{- url -}} diff --git a/_includes/js-selector.html b/_includes/js-selector.html new file mode 100644 index 0000000..9965107 --- /dev/null +++ b/_includes/js-selector.html @@ -0,0 +1,106 @@ + + + + +{% assign urls = site.data.origin[type].search.js %} + + + +{% if page.layout == 'post' or page.layout == 'page' or page.layout == 'home' %} + {% assign urls = urls | append: ',' | append: site.data.origin[type]['lazy-polyfill'].js %} + + {% unless page.layout == 'home' %} + + {% assign urls = urls + | append: ',' + | append: site.data.origin[type].glightbox.js + | append: ',' + | append: site.data.origin[type].clipboard.js + %} + {% endunless %} +{% endif %} + +{% if page.layout == 'home' + or page.layout == 'post' + or page.layout == 'archives' + or page.layout == 'category' + or page.layout == 'tag' +%} + {% assign locale = include.lang | split: '-' | first %} + + {% assign urls = urls + | append: ',' + | append: site.data.origin[type].dayjs.js.common + | append: ',' + | append: site.data.origin[type].dayjs.js.locale + | replace: ':LOCALE', locale + | append: ',' + | append: site.data.origin[type].dayjs.js.relativeTime + | append: ',' + | append: site.data.origin[type].dayjs.js.localizedFormat + %} +{% endif %} + +{% if page.content contains ' + +{% if page.math %} + + + + +{% endif %} + + +{% if page.layout == 'post' %} + {% assign provider = site.pageviews.provider %} + + {% if provider and provider != empty %} + {% case provider %} + {% when 'goatcounter' %} + {% if site.analytics[provider].id != empty and site.analytics[provider].id %} + {% include pageviews/{{ provider }}.html %} + {% endif %} + {% endcase %} + {% endif %} +{% endif %} + +{% if page.mermaid %} + {% include mermaid.html %} +{% endif %} + +{% if jekyll.environment == 'production' %} + + {% if site.pwa.enabled %} + + {% endif %} + + + {% for analytics in site.analytics %} + {% capture str %}{{ analytics }}{% endcapture %} + {% assign type = str | split: '{' | first %} + {% if site.analytics[type].id and site.analytics[type].id != empty %} + {% include analytics/{{ type }}.html %} + {% endif %} + {% endfor %} +{% endif %} diff --git a/_includes/jsdelivr-combine.html b/_includes/jsdelivr-combine.html new file mode 100644 index 0000000..cffa699 --- /dev/null +++ b/_includes/jsdelivr-combine.html @@ -0,0 +1,26 @@ +{% assign urls = include.urls | split: ',' %} + +{% assign combined_urls = nil %} + +{% assign domain = 'https://cdn.jsdelivr.net/' %} + +{% for url in urls %} + {% if url contains domain %} + {% assign url_snippet = url | slice: domain.size, url.size %} + + {% if combined_urls %} + {% assign combined_urls = combined_urls | append: ',' | append: url_snippet %} + {% else %} + {% assign combined_urls = domain | append: 'combine/' | append: url_snippet %} + {% endif %} + + {% elsif url contains '//' %} + + {% else %} + + {% endif %} +{% endfor %} + +{% if combined_urls %} + +{% endif %} diff --git a/_includes/lang.html b/_includes/lang.html new file mode 100644 index 0000000..34b50df --- /dev/null +++ b/_includes/lang.html @@ -0,0 +1,10 @@ +{% comment %} + Detect appearance language and return it through variable "lang" +{% endcomment %} +{% if site.data.locales[page.lang] %} + {% assign lang = page.lang %} +{% elsif site.data.locales[site.lang] %} + {% assign lang = site.lang %} +{% else %} + {% assign lang = 'en' %} +{% endif %} diff --git a/_includes/language-alias.html b/_includes/language-alias.html new file mode 100644 index 0000000..abfa7ba --- /dev/null +++ b/_includes/language-alias.html @@ -0,0 +1,70 @@ +{% comment %} + + Convert the alias of the syntax language to the official name + + See: + +{% endcomment %} + +{% assign _lang = include.language | default: '' %} + +{% case _lang %} + {% when 'actionscript', 'as', 'as3' %} + {{ 'ActionScript' }} + {% when 'applescript' %} + {{ 'AppleScript' }} + {% when 'brightscript', 'bs', 'brs' %} + {{ 'BrightScript' }} + {% when 'cfscript', 'cfc' %} + {{ 'CFScript' }} + {% when 'coffeescript', 'coffee', 'coffee-script' %} + {{ 'CoffeeScript' }} + {% when 'cs', 'csharp' %} + {{ 'C#' }} + {% when 'erl' %} + {{ 'Erlang' }} + {% when 'graphql' %} + {{ 'GraphQL' }} + {% when 'haskell', 'hs' %} + {{ 'Haskell' }} + {% when 'javascript', 'js' %} + {{ 'JavaScript' }} + {% when 'make', 'mf', 'gnumake', 'bsdmake' %} + {{ 'Makefile' }} + {% when 'md', 'mkd' %} + {{ 'Markdown' }} + {% when 'm' %} + {{ 'Matlab' }} + {% when 'objective_c', 'objc', 'obj-c', 'obj_c', 'objectivec' %} + {{ 'Objective-C' }} + {% when 'perl', 'pl' %} + {{ 'Perl' }} + {% when 'php','php3','php4','php5' %} + {{ 'PHP' }} + {% when 'py' %} + {{ 'Python' }} + {% when 'rb' %} + {{ 'Ruby' }} + {% when 'rs','no_run','ignore','should_panic' %} + {{ 'Rust' }} + {% when 'bash', 'zsh', 'ksh', 'sh' %} + {{ 'Shell' }} + {% when 'st', 'squeak' %} + {{ 'Smalltalk' }} + {% when 'tex'%} + {{ 'TeX' }} + {% when 'latex' %} + {{ 'LaTex' }} + {% when 'ts', 'typescript' %} + {{ 'TypeScript' }} + {% when 'vb', 'visualbasic' %} + {{ 'Visual Basic' }} + {% when 'vue', 'vuejs' %} + {{ 'Vue.js' }} + {% when 'yml' %} + {{ 'YAML' }} + {% when 'css', 'html', 'scss', 'ssh', 'toml', 'xml', 'yaml', 'json' %} + {{ _lang | upcase }} + {% else %} + {{ _lang | capitalize }} +{% endcase %} diff --git a/_includes/media-url.html b/_includes/media-url.html new file mode 100644 index 0000000..ea41075 --- /dev/null +++ b/_includes/media-url.html @@ -0,0 +1,37 @@ +{%- comment -%} + Generate media resource final URL based on `site.cdn`, `page.media_subpath` + + Arguments: + src - required, basic media resources path + subpath - optional, relative path of media resources + absolute - optional, boolean, if true, generate absolute URL + + Return: + media resources URL +{%- endcomment -%} + +{% assign url = include.src %} + +{%- if url -%} + {% unless url contains ':' %} + {%- comment -%} Add media resources subpath prefix {%- endcomment -%} + {% assign url = include.subpath | default: '' | append: '/' | append: url %} + + {%- comment -%} Prepend CND URL {%- endcomment -%} + {% if site.cdn %} + {% assign url = site.cdn | append: '/' | append: url %} + {% endif %} + + {% assign url = url | replace: '///', '/' | replace: '//', '/' | replace: ':/', '://' %} + + {% unless url contains '://' %} + {% if include.absolute %} + {% assign url = site.url | append: site.baseurl | append: url %} + {% else %} + {% assign url = site.baseurl | append: url %} + {% endif %} + {% endunless %} + {% endunless %} +{%- endif -%} + +{{- url -}} diff --git a/_includes/mermaid.html b/_includes/mermaid.html new file mode 100644 index 0000000..a3a83ed --- /dev/null +++ b/_includes/mermaid.html @@ -0,0 +1,62 @@ + + diff --git a/_includes/metadata-hook.html b/_includes/metadata-hook.html new file mode 100644 index 0000000..fd7e9bd --- /dev/null +++ b/_includes/metadata-hook.html @@ -0,0 +1 @@ + diff --git a/_includes/mode-toggle.html b/_includes/mode-toggle.html new file mode 100644 index 0000000..113ec37 --- /dev/null +++ b/_includes/mode-toggle.html @@ -0,0 +1,116 @@ + + + diff --git a/_includes/no-linenos.html b/_includes/no-linenos.html new file mode 100644 index 0000000..8500693 --- /dev/null +++ b/_includes/no-linenos.html @@ -0,0 +1,10 @@ +{% comment %} + Remove the line number of the code snippet. +{% endcomment %} + +{% assign content = include.content %} + +{% if content contains '
' %}
+  {% assign content = content | replace: '
', '' %}
+{% endif %}
diff --git a/_includes/notification.html b/_includes/notification.html
new file mode 100644
index 0000000..80049b0
--- /dev/null
+++ b/_includes/notification.html
@@ -0,0 +1,24 @@
+
diff --git a/_includes/origin-type.html b/_includes/origin-type.html
new file mode 100644
index 0000000..7f72012
--- /dev/null
+++ b/_includes/origin-type.html
@@ -0,0 +1,13 @@
+{% comment %} Site static assets origin type {% endcomment %}
+
+{% assign type = 'cors' %}
+
+{% if site.assets.self_host.enabled %}
+  {% if site.assets.self_host.env %}
+    {% if site.assets.self_host.env == jekyll.environment %}
+      {% assign type = 'basic' %}
+    {% endif %}
+  {% else %}
+    {% assign type = 'basic' %}
+  {% endif %}
+{% endif %}
diff --git a/_includes/pageviews/goatcounter.html b/_includes/pageviews/goatcounter.html
new file mode 100644
index 0000000..e62fd69
--- /dev/null
+++ b/_includes/pageviews/goatcounter.html
@@ -0,0 +1,19 @@
+
+
diff --git a/_includes/post-description.html b/_includes/post-description.html
new file mode 100644
index 0000000..6c40036
--- /dev/null
+++ b/_includes/post-description.html
@@ -0,0 +1,16 @@
+{%- comment -%}
+  Get post description or generate it from the post content.
+{%- endcomment -%}
+
+{%- assign max_length = include.max_length | default: 200 -%}
+
+{%- capture description -%}
+{%- if post.description -%}
+  {{- post.description -}}
+{%- else -%}
+  {%- include no-linenos.html content=post.content -%}
+  {{- content | markdownify | strip_html -}}
+{%- endif -%}
+{%- endcapture -%}
+
+{{- description | strip | truncate: max_length | escape -}}
diff --git a/_includes/post-nav.html b/_includes/post-nav.html
new file mode 100644
index 0000000..736bec3
--- /dev/null
+++ b/_includes/post-nav.html
@@ -0,0 +1,34 @@
+
+
+
diff --git a/_includes/post-paginator.html b/_includes/post-paginator.html
new file mode 100644
index 0000000..c74e978
--- /dev/null
+++ b/_includes/post-paginator.html
@@ -0,0 +1,91 @@
+
+
+
+
diff --git a/_includes/post-sharing.html b/_includes/post-sharing.html
new file mode 100644
index 0000000..d894199
--- /dev/null
+++ b/_includes/post-sharing.html
@@ -0,0 +1,52 @@
+
+
+
diff --git a/_includes/read-time.html b/_includes/read-time.html
new file mode 100644
index 0000000..9952410
--- /dev/null
+++ b/_includes/read-time.html
@@ -0,0 +1,37 @@
+
+
+{% assign words = include.content | strip_html | number_of_words: 'auto' %}
+
+
+
+{% assign wpm = 180 %}
+{% assign min_time = 1 %}
+
+{% assign read_time = words | divided_by: wpm %}
+
+{% unless read_time > 0 %}
+  {% assign read_time = min_time %}
+{% endunless %}
+
+{% capture read_prompt %}
+  {{- site.data.locales[include.lang].post.read_time.prompt -}}
+{% endcapture %}
+
+
+
+  
+    {{- read_time -}}
+    {{ ' ' }}
+    {{- site.data.locales[include.lang].post.read_time.unit -}}
+  
+  {%- if include.prompt -%}
+    {%- assign _prompt_words = read_prompt | number_of_words: 'auto' -%}
+    {%- unless _prompt_words > 1 -%}{{ ' ' }}{%- endunless -%}
+    {{ read_prompt }}
+  {%- endif -%}
+
diff --git a/_includes/refactor-content.html b/_includes/refactor-content.html
new file mode 100644
index 0000000..8d298cd
--- /dev/null
+++ b/_includes/refactor-content.html
@@ -0,0 +1,255 @@
+
+
+{% assign _content = include.content %}
+
+
+
+{% if _content contains '', ''
+    | replace: '
', '' + | replace: '
', '
' + %} +{% endif %} + + + +{% if _content contains '
' %}
+  {% assign _content = _content
+    | replace: '
', '' + %} +{% endif %} + + + +{% if _content contains '', + '' + | replace: '', + '' + %} +{% endif %} + + + +{% assign IMG_TAG = '' | first %} + {% assign _right = _img_snippet | remove: _left %} + + {% unless _left contains 'src=' %} + {% continue %} + {% endunless %} + + {% assign _left = _left | remove: ' /' | replace: ' w=', ' width=' | replace: ' h=', ' height=' %} + {% assign _attrs = _left | split: '" ' %} + + {% assign _src = null %} + {% assign _lqip = null %} + {% assign _class = null %} + + {% for _attr in _attrs %} + {% unless _attr contains '=' %} + {% continue %} + {% endunless %} + + {% assign _pair = _attr | split: '="' %} + {% capture _key %}{{ _pair | first }}{% endcapture %} + {% capture _value %}{{ _pair | last | remove: '"' }}{% endcapture %} + + {% case _key %} + {% when 'src' %} + {% assign _src = _value %} + {% when 'lqip' %} + {% assign _lqip = _value %} + {% when 'class' %} + {% assign _class = _value %} + {% endcase %} + {% endfor %} + + + {% if _class %} + {% capture _old_class %}class="{{ _class }}"{% endcapture %} + {% assign _left = _left | remove: _old_class %} + {% endif %} + + {% assign _final_src = null %} + {% assign _lazyload = true %} + + {%- capture _img_url -%} + {% include media-url.html src=_src subpath=page.media_subpath %} + {%- endcapture -%} + + {% assign _path_prefix = _img_url | remove: _src %} + + {% unless _src contains '//' %} + {% assign _final_src = _path_prefix | append: _src %} + {% assign _src_alt = 'src="' | append: _path_prefix %} + {% assign _left = _left | replace: 'src="', _src_alt %} + {% endunless %} + + {% if _lqip %} + {% assign _lazyload = false %} + {% assign _class = _class | append: ' blur' %} + + {% unless _lqip contains 'data:' %} + {% assign _lqip_alt = 'lqip="' | append: _path_prefix %} + {% assign _left = _left | replace: 'lqip="', _lqip_alt %} + {% endunless %} + + + {% assign _left = _left | replace: 'src=', 'data-src=' | replace: ' lqip=', ' data-lqip="true" src=' %} + + {% else %} + {% assign _class = _class | append: ' shimmer' %} + {% endif %} + + + {% if _lazyload %} + {% assign _left = _left | append: ' loading="lazy"' %} + {% endif %} + + {% if page.layout == 'home' %} + + {% assign _wrapper_start = '
' %} + + {% assign _img_content = _img_content | append: _wrapper_start %} + {% assign _right = _right | prepend: '>` is wrapped by `` --> + {% assign _parent = _right | slice: 1, 4 %} + + {% if _parent == '' %} + + {% assign _size = _img_content | size | minus: 1 %} + {% capture _class %} + class="img-link{% unless _lqip %} shimmer{% endunless %}" + {% endcapture %} + {% assign _img_content = _img_content | slice: 0, _size | append: _class | append: '>' %} + + {% else %} + + {% assign _wrapper_start = _final_src + | default: _src + | prepend: '' + %} + + {% assign _img_content = _img_content | append: _wrapper_start %} + {% assign _right = '> + {% assign _img_content = _img_content | append: IMG_TAG | append: _left | append: _right %} + {% endfor %} + + {% if _img_content %} + {% assign _content = _img_content %} + {% endif %} +{% endif %} + + + +{% if _content contains '
' %} + {% assign _code_spippets = _content | split: '
' %} + {% assign _new_content = '' %} + + {% for _snippet in _code_spippets %} + {% if forloop.last %} + {% assign _new_content = _new_content | append: _snippet %} + + {% else %} + {% assign _left = _snippet | split: '><' | last %} + + {% if _left contains 'file="' %} + {% assign _label_text = _left | split: 'file="' | last | split: '"' | first %} + {% assign _label_icon = 'far fa-file-code fa-fw' %} + {% else %} + {% assign _lang = _left | split: 'language-' | last | split: ' ' | first %} + {% capture _label_text %}{% include language-alias.html language=_lang %}{% endcapture %} + {% assign _label_icon = 'fas fa-code fa-fw small' %} + {% endif %} + + {% capture _label %} + + {% endcapture %} + + {% assign _new_content = _new_content + | append: _snippet + | append: '
' + | append: _label + | append: '
' + | append: '
' + %} + {% endif %} + {% endfor %} + + {% assign _content = _new_content %} +{% endif %} + + + +{% assign heading_levels = '2,3,4,5' | split: ',' %} +{% assign _heading_content = _content %} + +{% for level in heading_levels %} + {% assign mark_start = '' + %} + + {% assign left = snippet | split: mark_end | first %} + {% assign right = snippet | slice: left.size, snippet.size %} + {% assign left = left | replace_first: '">', '">' | append: '' %} + + {% assign _new_content = _new_content | append: mark_start | append: left | append: anchor | append: right %} + {% endfor %} + + {% assign _heading_content = _new_content %} + {% endif %} +{% endfor %} + +{% assign _content = _heading_content %} + + +{{ _content }} diff --git a/_includes/related-posts.html b/_includes/related-posts.html new file mode 100644 index 0000000..37a295b --- /dev/null +++ b/_includes/related-posts.html @@ -0,0 +1,94 @@ + + + +{% assign TOTAL_SIZE = 3 %} + + +{% assign TAG_SCORE = 1 %} + + +{% assign CATEGORY_SCORE = 0.5 %} + +{% assign SEPARATOR = ':' %} + +{% assign match_posts = '' | split: '' %} + +{% for category in page.categories %} + {% assign match_posts = match_posts | push: site.categories[category] | uniq %} +{% endfor %} + +{% for tag in page.tags %} + {% assign match_posts = match_posts | push: site.tags[tag] | uniq %} +{% endfor %} + +{% assign match_posts = match_posts | reverse %} +{% assign last_index = match_posts.size | minus: 1 %} +{% assign score_list = '' | split: '' %} + +{% for i in (0..last_index) %} + {% assign post = match_posts[i] %} + + {% if post.url == page.url %} + {% continue %} + {% endif %} + + {% assign score = 0 %} + + {% for tag in post.tags %} + {% if page.tags contains tag %} + {% assign score = score | plus: TAG_SCORE %} + {% endif %} + {% endfor %} + + {% for category in post.categories %} + {% if page.categories contains category %} + {% assign score = score | plus: CATEGORY_SCORE %} + {% endif %} + {% endfor %} + + {% if score > 0 %} + {% capture score_item %}{{ score }}{{ SEPARATOR }}{{ i }}{% endcapture %} + {% assign score_list = score_list | push: score_item %} + {% endif %} +{% endfor %} + +{% assign index_list = '' | split: '' %} + +{% if score_list.size > 0 %} + {% assign score_list = score_list | sort | reverse %} + {% for entry in score_list limit: TOTAL_SIZE %} + {% assign index = entry | split: SEPARATOR | last %} + {% assign index_list = index_list | push: index %} + {% endfor %} +{% endif %} + +{% assign relate_posts = '' | split: '' %} + +{% for index in index_list %} + {% assign i = index | to_integer %} + {% assign relate_posts = relate_posts | push: match_posts[i] %} +{% endfor %} + +{% if relate_posts.size > 0 %} + + +{% endif %} diff --git a/_includes/search-loader.html b/_includes/search-loader.html new file mode 100644 index 0000000..2582580 --- /dev/null +++ b/_includes/search-loader.html @@ -0,0 +1,47 @@ + + +{% capture result_elem %} +
+
+

{title}

+ +
+

{snippet}

+
+{% endcapture %} + +{% capture not_found %}

{{ site.data.locales[include.lang].search.no_results }}

{% endcapture %} + + diff --git a/_includes/search-results.html b/_includes/search-results.html new file mode 100644 index 0000000..00a3182 --- /dev/null +++ b/_includes/search-results.html @@ -0,0 +1,10 @@ + + +
+
+
+ {% include_cached trending-tags.html %} +
+
+
+
diff --git a/_includes/sidebar.html b/_includes/sidebar.html new file mode 100644 index 0000000..4f0bb8c --- /dev/null +++ b/_includes/sidebar.html @@ -0,0 +1,99 @@ + + + + diff --git a/_includes/toc.html b/_includes/toc.html new file mode 100644 index 0000000..15eb934 --- /dev/null +++ b/_includes/toc.html @@ -0,0 +1,13 @@ +{% assign enable_toc = false %} +{% if site.toc and page.toc %} + {% if page.content contains ' +

{{- site.data.locales[include.lang].panel.toc -}}

+ + +{% endif %} diff --git a/_includes/topbar.html b/_includes/topbar.html new file mode 100644 index 0000000..fd68d1f --- /dev/null +++ b/_includes/topbar.html @@ -0,0 +1,77 @@ + + +
+
+ + + + + +
+ {% if page.layout == 'home' %} + {{- site.data.locales[include.lang].title | default: site.title -}} + {% elsif page.collection == 'tabs' or page.layout == 'page' %} + {%- capture tab_key -%}{{ page.url | split: '/' }}{%- endcapture -%} + {{- site.data.locales[include.lang].tabs[tab_key] | default: page.title -}} + {% else %} + {{- site.data.locales[include.lang].layout[page.layout] | default: page.layout | capitalize -}} + {% endif %} +
+ + + + + + + + +
+
diff --git a/_includes/trending-tags.html b/_includes/trending-tags.html new file mode 100644 index 0000000..57369f0 --- /dev/null +++ b/_includes/trending-tags.html @@ -0,0 +1,46 @@ + + +{% assign MAX = 10 %} + +{% assign size_list = '' | split: '' %} +{% assign tag_list = '' | split: '' %} + +{% for tag in site.tags %} + {% assign size = tag | last | size %} + {% assign size_list = size_list | push: size %} + + {% assign tag_str = tag | first | append: '::' | append: size %} + {% assign tag_list = tag_list | push: tag_str %} +{% endfor %} + +{% assign size_list = size_list | sort | reverse %} + +{% assign tag_list = tag_list | sort_natural %} + +{% assign trending_tags = '' | split: '' %} + +{% for size in size_list limit: MAX %} + {% for tag_str in tag_list %} + {% assign tag = tag_str | split: '::' %} + {% assign tag_name = tag | first %} + {% assign tag_size = tag | last | plus: 0 %} + {% if tag_size == size %} + {% unless trending_tags contains tag_name %} + {% assign trending_tags = trending_tags | push: tag_name %} + {% break %} + {% endunless %} + {% endif %} + {% endfor %} +{% endfor %} + +{% if trending_tags.size > 0 %} +
+

{{- site.data.locales[include.lang].panel.trending_tags -}}

+
+ {% for tag_name in trending_tags %} + {% assign url = tag_name | slugify | url_encode | prepend: '/tags/' | append: '/' %} + + {% endfor %} +
+
+{% endif %} diff --git a/_includes/update-list.html b/_includes/update-list.html new file mode 100644 index 0000000..93684c3 --- /dev/null +++ b/_includes/update-list.html @@ -0,0 +1,40 @@ + + +{% assign MAX_SIZE = 5 %} + +{% assign all_list = '' | split: '' %} + +{% for post in site.posts %} + {% assign datetime = post.last_modified_at | default: post.date %} + + {% capture elem %} + {{- datetime | date: "%Y%m%d%H%M%S" -}}::{{- forloop.index0 -}} + {% endcapture %} + + {% assign all_list = all_list | push: elem %} +{% endfor %} + +{% assign all_list = all_list | sort | reverse %} + +{% assign update_list = '' | split: '' %} + +{% for entry in all_list limit: MAX_SIZE %} + {% assign update_list = update_list | push: entry %} +{% endfor %} + +{% if update_list.size > 0 %} +
+

{{- site.data.locales[include.lang].panel.lastmod -}}

+
    + {% for item in update_list %} + {% assign index = item | split: '::' | last | plus: 0 %} + {% assign post = site.posts[index] %} + {% assign url = post.url | relative_url %} +
  • + {{ post.title }} +
  • + {% endfor %} +
+
+ +{% endif %} diff --git a/_javascript/categories.js b/_javascript/categories.js new file mode 100644 index 0000000..15d8251 --- /dev/null +++ b/_javascript/categories.js @@ -0,0 +1,7 @@ +import { basic, initSidebar, initTopbar } from './modules/layouts'; +import { categoryCollapse } from './modules/plugins'; + +basic(); +initSidebar(); +initTopbar(); +categoryCollapse(); diff --git a/_javascript/commons.js b/_javascript/commons.js new file mode 100644 index 0000000..6a17fb9 --- /dev/null +++ b/_javascript/commons.js @@ -0,0 +1,5 @@ +import { basic, initSidebar, initTopbar } from './modules/layouts'; + +initSidebar(); +initTopbar(); +basic(); diff --git a/_javascript/home.js b/_javascript/home.js new file mode 100644 index 0000000..ef22cb9 --- /dev/null +++ b/_javascript/home.js @@ -0,0 +1,8 @@ +import { basic, initSidebar, initTopbar } from './modules/layouts'; +import { initLocaleDatetime, loadImg } from './modules/plugins'; + +loadImg(); +initLocaleDatetime(); +initSidebar(); +initTopbar(); +basic(); diff --git a/_javascript/misc.js b/_javascript/misc.js new file mode 100644 index 0000000..52b4043 --- /dev/null +++ b/_javascript/misc.js @@ -0,0 +1,7 @@ +import { basic, initSidebar, initTopbar } from './modules/layouts'; +import { initLocaleDatetime } from './modules/plugins'; + +initSidebar(); +initTopbar(); +initLocaleDatetime(); +basic(); diff --git a/_javascript/modules/components/back-to-top.js b/_javascript/modules/components/back-to-top.js new file mode 100644 index 0000000..40d9cd1 --- /dev/null +++ b/_javascript/modules/components/back-to-top.js @@ -0,0 +1,19 @@ +/** + * Reference: https://bootsnipp.com/snippets/featured/link-to-top-page + */ + +export function back2top() { + const btn = document.getElementById('back-to-top'); + + window.addEventListener('scroll', () => { + if (window.scrollY > 50) { + btn.classList.add('show'); + } else { + btn.classList.remove('show'); + } + }); + + btn.addEventListener('click', () => { + window.scrollTo({ top: 0 }); + }); +} diff --git a/_javascript/modules/components/category-collapse.js b/_javascript/modules/components/category-collapse.js new file mode 100644 index 0000000..0c53cb4 --- /dev/null +++ b/_javascript/modules/components/category-collapse.js @@ -0,0 +1,36 @@ +/** + * Tab 'Categories' expand/close effect. + */ + +import 'bootstrap/js/src/collapse.js'; + +const childPrefix = 'l_'; +const parentPrefix = 'h_'; +const children = document.getElementsByClassName('collapse'); + +export function categoryCollapse() { + [...children].forEach((elem) => { + const id = parentPrefix + elem.id.substring(childPrefix.length); + const parent = document.getElementById(id); + + // collapse sub-categories + elem.addEventListener('hide.bs.collapse', () => { + if (parent) { + parent.querySelector('.far.fa-folder-open').className = + 'far fa-folder fa-fw'; + parent.querySelector('.fas.fa-angle-down').classList.add('rotate'); + parent.classList.remove('hide-border-bottom'); + } + }); + + // expand sub-categories + elem.addEventListener('show.bs.collapse', () => { + if (parent) { + parent.querySelector('.far.fa-folder').className = + 'far fa-folder-open fa-fw'; + parent.querySelector('.fas.fa-angle-down').classList.remove('rotate'); + parent.classList.add('hide-border-bottom'); + } + }); + }); +} diff --git a/_javascript/modules/components/clipboard.js b/_javascript/modules/components/clipboard.js new file mode 100644 index 0000000..9566e9d --- /dev/null +++ b/_javascript/modules/components/clipboard.js @@ -0,0 +1,143 @@ +/** + * Clipboard functions + * + * Dependencies: + * clipboard.js (https://github.com/zenorocha/clipboard.js) + */ + +import Tooltip from 'bootstrap/js/src/tooltip'; + +const clipboardSelector = '.code-header>button'; + +const ICON_DEFAULT = 'far fa-clipboard'; +const ICON_SUCCESS = 'fas fa-check'; + +const ATTR_TIMEOUT = 'timeout'; +const ATTR_TITLE_SUCCEED = 'data-title-succeed'; +const ATTR_TITLE_ORIGIN = 'data-bs-original-title'; +const TIMEOUT = 2000; // in milliseconds + +function isLocked(node) { + if (node.hasAttribute(ATTR_TIMEOUT)) { + let timeout = node.getAttribute(ATTR_TIMEOUT); + if (Number(timeout) > Date.now()) { + return true; + } + } + + return false; +} + +function lock(node) { + node.setAttribute(ATTR_TIMEOUT, Date.now() + TIMEOUT); +} + +function unlock(node) { + node.removeAttribute(ATTR_TIMEOUT); +} + +function showTooltip(btn) { + const succeedTitle = btn.getAttribute(ATTR_TITLE_SUCCEED); + btn.setAttribute(ATTR_TITLE_ORIGIN, succeedTitle); + Tooltip.getInstance(btn).show(); +} + +function hideTooltip(btn) { + Tooltip.getInstance(btn).hide(); + btn.removeAttribute(ATTR_TITLE_ORIGIN); +} + +function setSuccessIcon(btn) { + const icon = btn.children[0]; + icon.setAttribute('class', ICON_SUCCESS); +} + +function resumeIcon(btn) { + const icon = btn.children[0]; + icon.setAttribute('class', ICON_DEFAULT); +} + +function setCodeClipboard() { + const clipboardList = document.querySelectorAll(clipboardSelector); + + if (clipboardList.length === 0) { + return; + } + + // Initial the clipboard.js object + const clipboard = new ClipboardJS(clipboardSelector, { + target: (trigger) => { + const codeBlock = trigger.parentNode.nextElementSibling; + return codeBlock.querySelector('code .rouge-code'); + } + }); + + [...clipboardList].map( + (elem) => + new Tooltip(elem, { + placement: 'left' + }) + ); + + clipboard.on('success', (e) => { + const trigger = e.trigger; + + e.clearSelection(); + + if (isLocked(trigger)) { + return; + } + + setSuccessIcon(trigger); + showTooltip(trigger); + lock(trigger); + + setTimeout(() => { + hideTooltip(trigger); + resumeIcon(trigger); + unlock(trigger); + }, TIMEOUT); + }); +} + +function setLinkClipboard() { + const btnCopyLink = document.getElementById('copy-link'); + + if (btnCopyLink === null) { + return; + } + + btnCopyLink.addEventListener('click', (e) => { + const target = e.target; + + if (isLocked(target)) { + return; + } + + // Copy URL to clipboard + navigator.clipboard.writeText(window.location.href).then(() => { + const defaultTitle = target.getAttribute(ATTR_TITLE_ORIGIN); + const succeedTitle = target.getAttribute(ATTR_TITLE_SUCCEED); + + // Switch tooltip title + target.setAttribute(ATTR_TITLE_ORIGIN, succeedTitle); + Tooltip.getInstance(target).show(); + + lock(target); + + setTimeout(() => { + target.setAttribute(ATTR_TITLE_ORIGIN, defaultTitle); + unlock(target); + }, TIMEOUT); + }); + }); + + btnCopyLink.addEventListener('mouseleave', (e) => { + Tooltip.getInstance(e.target).hide(); + }); +} + +export function initClipboard() { + setCodeClipboard(); + setLinkClipboard(); +} diff --git a/_javascript/modules/components/img-loading.js b/_javascript/modules/components/img-loading.js new file mode 100644 index 0000000..989d9e6 --- /dev/null +++ b/_javascript/modules/components/img-loading.js @@ -0,0 +1,67 @@ +/** + * Setting up image lazy loading and LQIP switching + */ + +const ATTR_DATA_SRC = 'data-src'; +const ATTR_DATA_LQIP = 'data-lqip'; + +const cover = { + SHIMMER: 'shimmer', + BLUR: 'blur' +}; + +function removeCover(clzss) { + this.parentElement.classList.remove(clzss); +} + +function handleImage() { + if (!this.complete) { + return; + } + + if (this.hasAttribute(ATTR_DATA_LQIP)) { + removeCover.call(this, cover.BLUR); + } else { + removeCover.call(this, cover.SHIMMER); + } +} + +/** + * Switches the LQIP with the real image URL. + */ +function switchLQIP() { + const src = this.getAttribute(ATTR_DATA_SRC); + this.setAttribute('src', encodeURI(src)); + this.removeAttribute(ATTR_DATA_SRC); +} + +export function loadImg() { + const images = document.querySelectorAll('article img'); + + if (images.length === 0) { + return; + } + + images.forEach((img) => { + img.addEventListener('load', handleImage); + }); + + // Images loaded from the browser cache do not trigger the 'load' event + document.querySelectorAll('article img[loading="lazy"]').forEach((img) => { + if (img.complete) { + removeCover.call(img, cover.SHIMMER); + } + }); + + // LQIPs set by the data URI or WebP will not trigger the 'load' event, + // so manually convert the URI to the URL of a high-resolution image. + const lqips = document.querySelectorAll( + `article img[${ATTR_DATA_LQIP}="true"]` + ); + + if (lqips.length) { + lqips.forEach((lqip) => { + switchLQIP.call(lqip); + }); + } +} diff --git a/_javascript/modules/components/img-popup.js b/_javascript/modules/components/img-popup.js new file mode 100644 index 0000000..b542a2e --- /dev/null +++ b/_javascript/modules/components/img-popup.js @@ -0,0 +1,48 @@ +/** + * Set up image popup + * + * Dependencies: https://github.com/biati-digital/glightbox + */ + +const html = document.documentElement; +const lightImages = '.popup:not(.dark)'; +const darkImages = '.popup:not(.light)'; +let selector = lightImages; + +if ( + (html.hasAttribute('data-mode') && + html.getAttribute('data-mode') === 'dark') || + (!html.hasAttribute('data-mode') && + window.matchMedia('(prefers-color-scheme: dark)').matches) +) { + selector = darkImages; +} + +let lightbox = GLightbox({ selector: `${selector}` }); + +function updateImages(event) { + if ( + event.source === window && + event.data && + event.data.direction === ModeToggle.ID + ) { + if (selector === lightImages) { + selector = darkImages; + } else { + selector = lightImages; + } + } + + lightbox.destroy(); + lightbox = GLightbox({ selector: `${selector}` }); +} + +export function imgPopup() { + if (document.querySelector(`${selector}`) === null) { + return; + } + + if (document.getElementById('mode-toggle')) { + window.addEventListener('message', updateImages); + } +} diff --git a/_javascript/modules/components/locale-datetime.js b/_javascript/modules/components/locale-datetime.js new file mode 100644 index 0000000..eb75626 --- /dev/null +++ b/_javascript/modules/components/locale-datetime.js @@ -0,0 +1,53 @@ +/** + * Update month/day to locale datetime + * + * Requirement: + */ + +/* A tool for locale datetime */ +class LocaleHelper { + static get attrTimestamp() { + return 'data-ts'; + } + + static get attrDateFormat() { + return 'data-df'; + } + + static get locale() { + return document.documentElement.getAttribute('lang').substring(0, 2); + } + + static getTimestamp(elem) { + return Number(elem.getAttribute(this.attrTimestamp)); // unix timestamp + } + + static getDateFormat(elem) { + return elem.getAttribute(this.attrDateFormat); + } +} + +export function initLocaleDatetime() { + dayjs.locale(LocaleHelper.locale); + dayjs.extend(window.dayjs_plugin_localizedFormat); + + document + .querySelectorAll(`[${LocaleHelper.attrTimestamp}]`) + .forEach((elem) => { + const date = dayjs.unix(LocaleHelper.getTimestamp(elem)); + const text = date.format(LocaleHelper.getDateFormat(elem)); + elem.textContent = text; + elem.removeAttribute(LocaleHelper.attrTimestamp); + elem.removeAttribute(LocaleHelper.attrDateFormat); + + // setup tooltips + if ( + elem.hasAttribute('data-bs-toggle') && + elem.getAttribute('data-bs-toggle') === 'tooltip' + ) { + // see: https://day.js.org/docs/en/display/format#list-of-localized-formats + const tooltipText = date.format('llll'); + elem.setAttribute('data-bs-title', tooltipText); + } + }); +} diff --git a/_javascript/modules/components/mode-watcher.js b/_javascript/modules/components/mode-watcher.js new file mode 100644 index 0000000..9eecd09 --- /dev/null +++ b/_javascript/modules/components/mode-watcher.js @@ -0,0 +1,14 @@ +/** + * Add listener for theme mode toggle + */ +const toggle = document.getElementById('mode-toggle'); + +export function modeWatcher() { + if (!toggle) { + return; + } + + toggle.addEventListener('click', () => { + modeToggle.flipMode(); + }); +} diff --git a/_javascript/modules/components/search-display.js b/_javascript/modules/components/search-display.js new file mode 100644 index 0000000..40059ac --- /dev/null +++ b/_javascript/modules/components/search-display.js @@ -0,0 +1,110 @@ +/** + * This script make #search-result-wrapper switch to unload or shown automatically. + */ + +const btnSbTrigger = document.getElementById('sidebar-trigger'); +const btnSearchTrigger = document.getElementById('search-trigger'); +const btnCancel = document.getElementById('search-cancel'); +const content = document.querySelectorAll('#main-wrapper>.container>.row'); +const topbarTitle = document.getElementById('topbar-title'); +const search = document.getElementById('search'); +const resultWrapper = document.getElementById('search-result-wrapper'); +const results = document.getElementById('search-results'); +const input = document.getElementById('search-input'); +const hints = document.getElementById('search-hints'); + +// CSS class names +const LOADED = 'd-block'; +const UNLOADED = 'd-none'; +const FOCUS = 'input-focus'; +const FLEX = 'd-flex'; + +/* Actions in mobile screens (Sidebar hidden) */ +class MobileSearchBar { + static on() { + btnSbTrigger.classList.add(UNLOADED); + topbarTitle.classList.add(UNLOADED); + btnSearchTrigger.classList.add(UNLOADED); + search.classList.add(FLEX); + btnCancel.classList.add(LOADED); + } + + static off() { + btnCancel.classList.remove(LOADED); + search.classList.remove(FLEX); + btnSbTrigger.classList.remove(UNLOADED); + topbarTitle.classList.remove(UNLOADED); + btnSearchTrigger.classList.remove(UNLOADED); + } +} + +class ResultSwitch { + static resultVisible = false; + + static on() { + if (!this.resultVisible) { + resultWrapper.classList.remove(UNLOADED); + content.forEach((el) => { + el.classList.add(UNLOADED); + }); + this.resultVisible = true; + } + } + + static off() { + if (this.resultVisible) { + results.innerHTML = ''; + + if (hints.classList.contains(UNLOADED)) { + hints.classList.remove(UNLOADED); + } + + resultWrapper.classList.add(UNLOADED); + content.forEach((el) => { + el.classList.remove(UNLOADED); + }); + input.textContent = ''; + this.resultVisible = false; + } + } +} + +function isMobileView() { + return btnCancel.classList.contains(LOADED); +} + +export function displaySearch() { + btnSearchTrigger.addEventListener('click', () => { + MobileSearchBar.on(); + ResultSwitch.on(); + input.focus(); + }); + + btnCancel.addEventListener('click', () => { + MobileSearchBar.off(); + ResultSwitch.off(); + }); + + input.addEventListener('focus', () => { + search.classList.add(FOCUS); + }); + + input.addEventListener('focusout', () => { + search.classList.remove(FOCUS); + }); + + input.addEventListener('input', () => { + if (input.value === '') { + if (isMobileView()) { + hints.classList.remove(UNLOADED); + } else { + ResultSwitch.off(); + } + } else { + ResultSwitch.on(); + if (isMobileView()) { + hints.classList.add(UNLOADED); + } + } + }); +} diff --git a/_javascript/modules/components/sidebar.js b/_javascript/modules/components/sidebar.js new file mode 100644 index 0000000..6b562d8 --- /dev/null +++ b/_javascript/modules/components/sidebar.js @@ -0,0 +1,27 @@ +/** + * Expand or close the sidebar in mobile screens. + */ + +const ATTR_DISPLAY = 'sidebar-display'; + +class SidebarUtil { + static isExpanded = false; + + static toggle() { + if (SidebarUtil.isExpanded === false) { + document.body.setAttribute(ATTR_DISPLAY, ''); + } else { + document.body.removeAttribute(ATTR_DISPLAY); + } + + SidebarUtil.isExpanded = !SidebarUtil.isExpanded; + } +} + +export function sidebarExpand() { + document + .getElementById('sidebar-trigger') + .addEventListener('click', SidebarUtil.toggle); + + document.getElementById('mask').addEventListener('click', SidebarUtil.toggle); +} diff --git a/_javascript/modules/components/toc.js b/_javascript/modules/components/toc.js new file mode 100644 index 0000000..56ce26f --- /dev/null +++ b/_javascript/modules/components/toc.js @@ -0,0 +1,15 @@ +export function toc() { + if (document.querySelector('main h2, main h3')) { + // see: https://github.com/tscanlin/tocbot#usage + tocbot.init({ + tocSelector: '#toc', + contentSelector: '.content', + ignoreSelector: '[data-toc-skip]', + headingSelector: 'h2, h3, h4', + orderedList: false, + scrollSmooth: false + }); + + document.getElementById('toc-wrapper').classList.remove('d-none'); + } +} diff --git a/_javascript/modules/components/tooltip-loader.js b/_javascript/modules/components/tooltip-loader.js new file mode 100644 index 0000000..c36c879 --- /dev/null +++ b/_javascript/modules/components/tooltip-loader.js @@ -0,0 +1,11 @@ +import Tooltip from 'bootstrap/js/src/tooltip'; + +export function loadTooptip() { + const tooltipTriggerList = document.querySelectorAll( + '[data-bs-toggle="tooltip"]' + ); + + [...tooltipTriggerList].map( + (tooltipTriggerEl) => new Tooltip(tooltipTriggerEl) + ); +} diff --git a/_javascript/modules/layouts.js b/_javascript/modules/layouts.js new file mode 100644 index 0000000..28f7962 --- /dev/null +++ b/_javascript/modules/layouts.js @@ -0,0 +1,3 @@ +export { basic } from './layouts/basic'; +export { initSidebar } from './layouts/sidebar'; +export { initTopbar } from './layouts/topbar'; diff --git a/_javascript/modules/layouts/basic.js b/_javascript/modules/layouts/basic.js new file mode 100644 index 0000000..fb36a8b --- /dev/null +++ b/_javascript/modules/layouts/basic.js @@ -0,0 +1,7 @@ +import { back2top } from '../components/back-to-top'; +import { loadTooptip } from '../components/tooltip-loader'; + +export function basic() { + back2top(); + loadTooptip(); +} diff --git a/_javascript/modules/layouts/sidebar.js b/_javascript/modules/layouts/sidebar.js new file mode 100644 index 0000000..8795693 --- /dev/null +++ b/_javascript/modules/layouts/sidebar.js @@ -0,0 +1,7 @@ +import { modeWatcher } from '../components/mode-watcher'; +import { sidebarExpand } from '../components/sidebar'; + +export function initSidebar() { + modeWatcher(); + sidebarExpand(); +} diff --git a/_javascript/modules/layouts/topbar.js b/_javascript/modules/layouts/topbar.js new file mode 100644 index 0000000..cfcd0ed --- /dev/null +++ b/_javascript/modules/layouts/topbar.js @@ -0,0 +1,5 @@ +import { displaySearch } from '../components/search-display'; + +export function initTopbar() { + displaySearch(); +} diff --git a/_javascript/modules/plugins.js b/_javascript/modules/plugins.js new file mode 100644 index 0000000..fb892e2 --- /dev/null +++ b/_javascript/modules/plugins.js @@ -0,0 +1,6 @@ +export { categoryCollapse } from './components/category-collapse'; +export { initClipboard } from './components/clipboard'; +export { loadImg } from './components/img-loading'; +export { imgPopup } from './components/img-popup'; +export { initLocaleDatetime } from './components/locale-datetime'; +export { toc } from './components/toc'; diff --git a/_javascript/page.js b/_javascript/page.js new file mode 100644 index 0000000..76e8ce9 --- /dev/null +++ b/_javascript/page.js @@ -0,0 +1,9 @@ +import { basic, initSidebar, initTopbar } from './modules/layouts'; +import { loadImg, imgPopup, initClipboard } from './modules/plugins'; + +loadImg(); +imgPopup(); +initSidebar(); +initTopbar(); +initClipboard(); +basic(); diff --git a/_javascript/post.js b/_javascript/post.js new file mode 100644 index 0000000..9340f05 --- /dev/null +++ b/_javascript/post.js @@ -0,0 +1,17 @@ +import { basic, initSidebar, initTopbar } from './modules/layouts'; +import { + loadImg, + imgPopup, + initLocaleDatetime, + initClipboard, + toc +} from './modules/plugins'; + +loadImg(); +toc(); +imgPopup(); +initSidebar(); +initLocaleDatetime(); +initClipboard(); +initTopbar(); +basic(); diff --git a/_javascript/pwa/app.js b/_javascript/pwa/app.js new file mode 100644 index 0000000..c71036a --- /dev/null +++ b/_javascript/pwa/app.js @@ -0,0 +1,51 @@ +import { pwa, baseurl } from '../../_config.yml'; +import Toast from 'bootstrap/js/src/toast'; + +if ('serviceWorker' in navigator) { + if (pwa.enabled) { + const swUrl = `${baseurl}/sw.min.js`; + const notification = document.getElementById('notification'); + const btnRefresh = notification.querySelector('.toast-body>button'); + const popupWindow = Toast.getOrCreateInstance(notification); + + navigator.serviceWorker.register(swUrl).then((registration) => { + // In case the user ignores the notification + if (registration.waiting) { + popupWindow.show(); + } + + registration.addEventListener('updatefound', () => { + registration.installing.addEventListener('statechange', () => { + if (registration.waiting) { + if (navigator.serviceWorker.controller) { + popupWindow.show(); + } + } + }); + }); + + btnRefresh.addEventListener('click', () => { + if (registration.waiting) { + registration.waiting.postMessage('SKIP_WAITING'); + } + popupWindow.hide(); + }); + }); + + let refreshing = false; + + // Detect controller change and refresh all the opened tabs + navigator.serviceWorker.addEventListener('controllerchange', () => { + if (!refreshing) { + window.location.reload(); + refreshing = true; + } + }); + } else { + navigator.serviceWorker.getRegistrations().then(function (registrations) { + for (let registration of registrations) { + registration.unregister(); + } + }); + } +} diff --git a/_javascript/pwa/sw.js b/_javascript/pwa/sw.js new file mode 100644 index 0000000..94b64bf --- /dev/null +++ b/_javascript/pwa/sw.js @@ -0,0 +1,94 @@ +import { baseurl } from '../../_config.yml'; + +importScripts(`${baseurl}/assets/js/data/swconf.js`); + +const purge = swconf.purge; +const interceptor = swconf.interceptor; + +function verifyUrl(url) { + const requestUrl = new URL(url); + const requestPath = requestUrl.pathname; + + if (!requestUrl.protocol.startsWith('http')) { + return false; + } + + for (const prefix of interceptor.urlPrefixes) { + if (requestUrl.href.startsWith(prefix)) { + return false; + } + } + + for (const path of interceptor.paths) { + if (requestPath.startsWith(path)) { + return false; + } + } + return true; +} + +self.addEventListener('install', (event) => { + if (purge) { + return; + } + + event.waitUntil( + caches.open(swconf.cacheName).then((cache) => { + return cache.addAll(swconf.resources); + }) + ); +}); + +self.addEventListener('activate', (event) => { + event.waitUntil( + caches.keys().then((keyList) => { + return Promise.all( + keyList.map((key) => { + if (purge) { + return caches.delete(key); + } else { + if (key !== swconf.cacheName) { + return caches.delete(key); + } + } + }) + ); + }) + ); +}); + +self.addEventListener('message', (event) => { + if (event.data === 'SKIP_WAITING') { + self.skipWaiting(); + } +}); + +self.addEventListener('fetch', (event) => { + if (event.request.headers.has('range')) { + return; + } + + event.respondWith( + caches.match(event.request).then((response) => { + if (response) { + return response; + } + + return fetch(event.request).then((response) => { + const url = event.request.url; + + if (purge || event.request.method !== 'GET' || !verifyUrl(url)) { + return response; + } + + // See: + let responseToCache = response.clone(); + + caches.open(swconf.cacheName).then((cache) => { + cache.put(event.request, responseToCache); + }); + return response; + }); + }) + ); +}); diff --git a/_layouts/compress.html b/_layouts/compress.html index bb34487..2779e92 100644 --- a/_layouts/compress.html +++ b/_layouts/compress.html @@ -1,10 +1,10 @@ --- # Jekyll layout that compresses HTML -# v3.1.0 +# v3.2.0 # http://jch.penibelst.de/ # © 2014–2015 Anatol Broder # MIT License --- {% capture _LINE_FEED %} -{% endcapture %}{% if site.compress_html.ignore.envs contains jekyll.environment or site.compress_html.ignore.envs == "all" %}{{ content }}{% else %}{% capture _content %}{{ content }}{% endcapture %}{% assign _profile = site.compress_html.profile %}{% if site.compress_html.endings == "all" %}{% assign _endings = "html head body li dt dd optgroup option colgroup caption thead tbody tfoot tr td th" | split: " " %}{% else %}{% assign _endings = site.compress_html.endings %}{% endif %}{% for _element in _endings %}{% capture _end %}{% endcapture %}{% assign _content = _content | remove: _end %}{% endfor %}{% if _profile and _endings %}{% assign _profile_endings = _content | size | plus: 1 %}{% endif %}{% for _element in site.compress_html.startings %}{% capture _start %}<{{ _element }}>{% endcapture %}{% assign _content = _content | remove: _start %}{% endfor %}{% if _profile and site.compress_html.startings %}{% assign _profile_startings = _content | size | plus: 1 %}{% endif %}{% if site.compress_html.comments == "all" %}{% assign _comments = "" | split: " " %}{% else %}{% assign _comments = site.compress_html.comments %}{% endif %}{% if _comments.size == 2 %}{% capture _comment_befores %}.{{ _content }}{% endcapture %}{% assign _comment_befores = _comment_befores | split: _comments.first %}{% for _comment_before in _comment_befores %}{% if forloop.first %}{% continue %}{% endif %}{% capture _comment_outside %}{% if _carry %}{{ _comments.first }}{% endif %}{{ _comment_before }}{% endcapture %}{% capture _comment %}{% unless _carry %}{{ _comments.first }}{% endunless %}{{ _comment_outside | split: _comments.last | first }}{% if _comment_outside contains _comments.last %}{{ _comments.last }}{% assign _carry = false %}{% else %}{% assign _carry = true %}{% endif %}{% endcapture %}{% assign _content = _content | remove_first: _comment %}{% endfor %}{% if _profile %}{% assign _profile_comments = _content | size | plus: 1 %}{% endif %}{% endif %}{% assign _pre_befores = _content | split: "" %}{% assign _pres_after = "" %}{% if _pres.size != 0 %}{% if site.compress_html.blanklines %}{% assign _lines = _pres.last | split: _LINE_FEED %}{% capture _pres_after %}{% for _line in _lines %}{% assign _trimmed = _line | split: " " | join: " " %}{% if _trimmed != empty or forloop.last %}{% unless forloop.first %}{{ _LINE_FEED }}{% endunless %}{{ _line }}{% endif %}{% endfor %}{% endcapture %}{% else %}{% assign _pres_after = _pres.last | split: " " | join: " " %}{% endif %}{% endif %}{% capture _content %}{{ _content }}{% if _pre_before contains "
" %}{% endif %}{% unless _pre_before contains "
" and _pres.size == 1 %}{{ _pres_after }}{% endunless %}{% endcapture %}{% endfor %}{% if _profile %}{% assign _profile_collapse = _content | size | plus: 1 %}{% endif %}{% if site.compress_html.clippings == "all" %}{% assign _clippings = "html head title base link meta style body article section nav aside h1 h2 h3 h4 h5 h6 hgroup header footer address p hr blockquote ol ul li dl dt dd figure figcaption main div table caption colgroup col tbody thead tfoot tr td th" | split: " " %}{% else %}{% assign _clippings = site.compress_html.clippings %}{% endif %}{% for _element in _clippings %}{% assign _edges = " ;; ;" | replace: "e", _element | split: ";" %}{% assign _content = _content | replace: _edges[0], _edges[1] | replace: _edges[2], _edges[3] | replace: _edges[4], _edges[5] %}{% endfor %}{% if _profile and _clippings %}{% assign _profile_clippings = _content | size | plus: 1 %}{% endif %}{{ _content }}{% if _profile %}
Step Bytes
raw {{ content | size }}{% if _profile_endings %}
endings {{ _profile_endings }}{% endif %}{% if _profile_startings %}
startings {{ _profile_startings }}{% endif %}{% if _profile_comments %}
comments {{ _profile_comments }}{% endif %}{% if _profile_collapse %}
collapse {{ _profile_collapse }}{% endif %}{% if _profile_clippings %}
clippings {{ _profile_clippings }}{% endif %}
{% endif %}{% endif %} +{% endcapture %}{% if site.compress_html.ignore.envs contains jekyll.environment or site.compress_html.ignore.envs == "all" or page.compress_html == false %}{{ content }}{% else %}{% capture _content %}{{ content }}{% endcapture %}{% assign _profile = site.compress_html.profile %}{% if site.compress_html.endings == "all" %}{% assign _endings = "html head body li dt dd optgroup option colgroup caption thead tbody tfoot tr td th" | split: " " %}{% else %}{% assign _endings = site.compress_html.endings %}{% endif %}{% for _element in _endings %}{% capture _end %}{% endcapture %}{% assign _content = _content | remove: _end %}{% endfor %}{% if _profile and _endings %}{% assign _profile_endings = _content | size | plus: 1 %}{% endif %}{% for _element in site.compress_html.startings %}{% capture _start %}<{{ _element }}>{% endcapture %}{% assign _content = _content | remove: _start %}{% endfor %}{% if _profile and site.compress_html.startings %}{% assign _profile_startings = _content | size | plus: 1 %}{% endif %}{% if site.compress_html.comments == "all" %}{% assign _comments = "" | split: " " %}{% else %}{% assign _comments = site.compress_html.comments %}{% endif %}{% if _comments.size == 2 %}{% capture _comment_befores %}.{{ _content }}{% endcapture %}{% assign _comment_befores = _comment_befores | split: _comments.first %}{% for _comment_before in _comment_befores %}{% if forloop.first %}{% continue %}{% endif %}{% capture _comment_outside %}{% if _carry %}{{ _comments.first }}{% endif %}{{ _comment_before }}{% endcapture %}{% capture _comment %}{% unless _carry %}{{ _comments.first }}{% endunless %}{{ _comment_outside | split: _comments.last | first }}{% if _comment_outside contains _comments.last %}{{ _comments.last }}{% assign _carry = false %}{% else %}{% assign _carry = true %}{% endif %}{% endcapture %}{% assign _content = _content | remove_first: _comment %}{% endfor %}{% if _profile %}{% assign _profile_comments = _content | size | plus: 1 %}{% endif %}{% endif %}{% assign _pre_befores = _content | split: "" %}{% assign _pres_after = "" %}{% if _pres.size != 0 %}{% if site.compress_html.blanklines %}{% assign _lines = _pres.last | split: _LINE_FEED %}{% capture _pres_after %}{% for _line in _lines %}{% assign _trimmed = _line | split: " " | join: " " %}{% if _trimmed != empty or forloop.last %}{% unless forloop.first %}{{ _LINE_FEED }}{% endunless %}{{ _line }}{% endif %}{% endfor %}{% endcapture %}{% else %}{% assign _pres_after = _pres.last | split: " " | join: " " %}{% endif %}{% endif %}{% capture _content %}{{ _content }}{% if _pre_before contains "
" %}{% endif %}{% unless _pre_before contains "" and _pres.size == 1 %}{{ _pres_after }}{% endunless %}{% endcapture %}{% endfor %}{% if _profile %}{% assign _profile_collapse = _content | size | plus: 1 %}{% endif %}{% if site.compress_html.clippings == "all" %}{% assign _clippings = "html head title base link meta style body article section nav aside h1 h2 h3 h4 h5 h6 hgroup header footer address p hr blockquote ol ul li dl dt dd figure figcaption main div table caption colgroup col tbody thead tfoot tr td th" | split: " " %}{% else %}{% assign _clippings = site.compress_html.clippings %}{% endif %}{% for _element in _clippings %}{% assign _edges = " ;; ;" | replace: "e", _element | split: ";" %}{% assign _content = _content | replace: _edges[0], _edges[1] | replace: _edges[2], _edges[3] | replace: _edges[4], _edges[5] %}{% endfor %}{% if _profile and _clippings %}{% assign _profile_clippings = _content | size | plus: 1 %}{% endif %}{{ _content }}{% if _profile %}
Step Bytes
raw {{ content | size }}{% if _profile_endings %}
endings {{ _profile_endings }}{% endif %}{% if _profile_startings %}
startings {{ _profile_startings }}{% endif %}{% if _profile_comments %}
comments {{ _profile_comments }}{% endif %}{% if _profile_collapse %}
collapse {{ _profile_collapse }}{% endif %}{% if _profile_clippings %}
clippings {{ _profile_clippings }}{% endif %}
{% endif %}{% endif %} diff --git a/_layouts/default.html b/_layouts/default.html index 097c7e9..ea438fe 100644 --- a/_layouts/default.html +++ b/_layouts/default.html @@ -13,12 +13,9 @@ layout: compress {% endif %} - + {% include head.html %} - {% if jekyll.environment == 'production' and site.google_analytics %} - {% include analytics.html %} - {% endif %} - + {% include sidebar.html lang=lang %} @@ -78,13 +75,8 @@ layout: compress {% endif %} + {% include js-selector.html lang=lang %} - {% include js-selector.html %} - - {% if page.mermaid %} - {% include mermaid.html %} - {% endif %} - - {% include_cached search-loader.html %} + {% include_cached search-loader.html lang=lang %} diff --git a/_layouts/home.html b/_layouts/home.html index 4cf4c1d..e44efe8 100644 --- a/_layouts/home.html +++ b/_layouts/home.html @@ -49,7 +49,7 @@ refactor: true {% if post.image %} {% assign src = post.image.path | default: post.image %} {% unless src contains '//' %} - {% assign src = post.img_path | append: '/' | append: src | replace: '//', '/' %} + {% assign src = post.media_subpath | append: '/' | append: src | replace: '//', '/' %} {% endunless %} {% assign alt = post.image.alt | xml_escape | default: 'Preview Image' %} @@ -72,10 +72,7 @@ refactor: true

{{ post.title }}

-

- {% include no-linenos.html content=post.content %} - {{ content | markdownify | strip_html | truncate: 200 | escape }} -

+

{% include post-description.html %}

-
diff --git a/_sass/addon/commons.scss b/_sass/addon/commons.scss new file mode 100644 index 0000000..c4c68e7 --- /dev/null +++ b/_sass/addon/commons.scss @@ -0,0 +1,1532 @@ +/* The common styles */ + +html { + font-size: 16px; + + @media (prefers-color-scheme: light) { + &:not([data-mode]), + &[data-mode='light'] { + @include light-scheme; + } + + &[data-mode='dark'] { + @include dark-scheme; + } + } + + @media (prefers-color-scheme: dark) { + &:not([data-mode]), + &[data-mode='dark'] { + @include dark-scheme; + } + + &[data-mode='light'] { + @include light-scheme; + } + } +} + +body { + background: var(--main-bg); + padding: env(safe-area-inset-top) env(safe-area-inset-right) + env(safe-area-inset-bottom) env(safe-area-inset-left); + color: var(--text-color); + -webkit-font-smoothing: antialiased; + font-family: $font-family-base; +} + +/* --- Typography --- */ + +@for $i from 1 through 5 { + h#{$i} { + @extend %heading; + + @if $i > 1 { + @extend %section; + @extend %anchor; + } + + @if $i < 5 { + $factor: 0.18rem; + + @if $i == 1 { + $factor: 0.23rem; + } + + font-size: 1rem + (5 - $i) * $factor; + } @else { + font-size: 1rem; + } + } +} + +a { + @extend %link-color; + + text-decoration: none; +} + +img { + max-width: 100%; + height: auto; + transition: all 0.35s ease-in-out; + + .blur & { + $blur: 20px; + + -webkit-filter: blur($blur); + filter: blur($blur); + } +} + +blockquote { + border-left: 5px solid var(--blockquote-border-color); + padding-left: 1rem; + color: var(--blockquote-text-color); + + > p:last-child { + margin-bottom: 0; + } + + &[class^='prompt-'] { + border-left: 0; + position: relative; + padding: 1rem 1rem 1rem 3rem; + color: var(--prompt-text-color); + + @extend %rounded; + + &::before { + text-align: center; + width: 3rem; + position: absolute; + left: 0.25rem; + margin-top: 0.4rem; + text-rendering: auto; + -webkit-font-smoothing: antialiased; + } + } + + @include prompt('tip', '\f0eb', $fa-style: 'regular'); + @include prompt('info', '\f06a', $rotate: 180); + @include prompt('warning', '\f06a'); + @include prompt('danger', '\f071'); +} + +kbd { + font-family: inherit; + display: inline-block; + vertical-align: middle; + line-height: 1.3rem; + min-width: 1.75rem; + text-align: center; + margin: 0 0.3rem; + padding-top: 0.1rem; + color: var(--kbd-text-color); + background-color: var(--kbd-bg-color); + border-radius: 0.25rem; + border: solid 1px var(--kbd-wrap-color); + box-shadow: inset 0 -2px 0 var(--kbd-wrap-color); +} + +hr { + border-color: var(--main-border-color); + opacity: 1; +} + +footer { + background-color: var(--main-bg); + height: $footer-height; + border-top: 1px solid var(--main-border-color); + + @extend %text-xs; + + a { + @extend %text-highlight; + + &:hover { + @extend %link-hover; + } + } + + em { + @extend %text-highlight; + } + + p { + text-align: center; + margin-bottom: 0; + } +} + +/* fontawesome icons */ +i { + &.far, + &.fas { + @extend %no-cursor; + } +} + +/* --- Panels --- */ + +.access { + top: 2rem; + transition: top 0.2s ease-in-out; + margin-top: 3rem; + margin-bottom: 4rem; + + &:only-child { + position: -webkit-sticky; + position: sticky; + } + + > section { + padding-left: 1rem; + border-left: 1px solid var(--main-border-color); + + &:not(:last-child) { + margin-bottom: 4rem; + } + } + + .content { + font-size: 0.9rem; + } +} + +#panel-wrapper { + /* the headings */ + .panel-heading { + font-family: inherit; + line-height: inherit; + + @include label(inherit); + } + + .post-tag { + line-height: 1.05rem; + font-size: 0.85rem; + border-radius: 0.8rem; + padding: 0.3rem 0.5rem; + margin: 0 0.35rem 0.5rem 0; + + &:hover { + transition: all 0.3s ease-in; + } + } +} + +#access-lastmod { + a { + color: inherit; + + &:hover { + @extend %link-hover; + } + + @extend %no-bottom-border; + } +} + +.footnotes > ol { + padding-left: 2rem; + margin-top: 0.5rem; + + > li { + &:not(:last-child) { + margin-bottom: 0.3rem; + } + + @extend %sup-fn-target; + + > p { + margin-left: 0.25em; + margin-top: 0; + margin-bottom: 0; + } + } +} + +.footnote { + @at-root a#{&} { + @include ml-mr(1px); + @include pl-pr(2px); + + border-bottom-style: none !important; + } +} + +sup { + @extend %sup-fn-target; +} + +.reversefootnote { + @at-root a#{&} { + font-size: 0.6rem; + line-height: 1; + position: relative; + bottom: 0.25em; + margin-left: 0.25em; + border-bottom-style: none !important; + } +} + +/* --- Begin of Markdown table style --- */ + +/* it will be created by Liquid */ +.table-wrapper { + overflow-x: auto; + margin-bottom: 1.5rem; + + > table { + min-width: 100%; + overflow-x: auto; + border-spacing: 0; + + thead { + border-bottom: solid 2px rgba(210, 215, 217, 0.75); + + th { + @extend %table-cell; + } + } + + tbody { + tr { + border-bottom: 1px solid var(--tb-border-color); + + &:nth-child(2n) { + background-color: var(--tb-even-bg); + } + + &:nth-child(2n + 1) { + background-color: var(--tb-odd-bg); + } + + td { + @extend %table-cell; + } + } + } /* tbody */ + } /* table */ +} + +/* --- post --- */ + +.preview-img { + aspect-ratio: 40 / 21; + width: 100%; + height: 100%; + overflow: hidden; + + @extend %rounded; + + &:not(.no-bg) { + background: var(--img-bg); + } + + img { + height: 100%; + -o-object-fit: cover; + object-fit: cover; + + @extend %rounded; + + @at-root #post-list & { + width: 100%; + } + } +} + +.post-preview { + @extend %rounded; + + border: 0; + background: var(--card-bg); + box-shadow: var(--card-shadow); + + &::before { + @extend %rounded; + + content: ''; + width: 100%; + height: 100%; + position: absolute; + background-color: var(--card-hovor-bg); + opacity: 0; + transition: opacity 0.35s ease-in-out; + } + + &:hover { + &::before { + opacity: 0.3; + } + } +} + +main { + line-height: 1.75; + + h1 { + margin-top: 2rem; + } + + p { + > a.popup { + &:not(.normal):not(.left):not(.right) { + @include align-center; + } + } + } + + .categories, + #tags, + #archives { + a:not(:hover) { + @extend %no-bottom-border; + } + } +} + +.post-meta { + @extend %text-sm; + + a { + &:not([class]):hover { + @extend %link-hover; + } + } + + em { + @extend %normal-font-style; + } +} + +.content { + font-size: 1.08rem; + margin-top: 2rem; + overflow-wrap: break-word; + + a { + &.popup { + @extend %no-cursor; + @extend %img-caption; + @include mt-mb(0.5rem); + + cursor: zoom-in; + } + + &:not(.img-link) { + @extend %link-underline; + + &:hover { + @extend %link-hover; + } + } + } + + ol, + ul { + &:not([class]), + &.task-list { + -webkit-padding-start: 1.75rem; + padding-inline-start: 1.75rem; + + li { + margin: 0.25rem 0; + padding-left: 0.25rem; + } + + ol, + ul { + -webkit-padding-start: 1.25rem; + padding-inline-start: 1.25rem; + margin: 0.5rem 0; + } + } + } + + ul.task-list { + -webkit-padding-start: 1.25rem; + padding-inline-start: 1.25rem; + + li { + list-style-type: none; + padding-left: 0; + + /* checkbox icon */ + > i { + width: 2rem; + margin-left: -1.25rem; + color: var(--checkbox-color); + + &.checked { + color: var(--checkbox-checked-color); + } + } + + ul { + -webkit-padding-start: 1.75rem; + padding-inline-start: 1.75rem; + } + } + + input[type='checkbox'] { + margin: 0 0.5rem 0.2rem -1.3rem; + vertical-align: middle; + } + } /* ul */ + + dl > dd { + margin-left: 1rem; + } + + ::marker { + color: var(--text-muted-color); + } +} /* .content */ + +.tag:hover { + @extend %tag-hover; +} + +.post-tag { + display: inline-block; + min-width: 2rem; + text-align: center; + border-radius: 0.5rem; + border: 1px solid var(--btn-border-color); + padding: 0 0.4rem; + color: var(--text-muted-color); + line-height: 1.3rem; + + &:not(:last-child) { + margin-right: 0.2rem; + } +} + +.rounded-10 { + border-radius: 10px !important; +} + +.img-link { + color: transparent; + display: inline-flex; +} + +.shimmer { + overflow: hidden; + position: relative; + background: var(--img-bg); + + &::before { + content: ''; + position: absolute; + background: var(--shimmer-bg); + height: 100%; + width: 100%; + -webkit-animation: shimmer 1.3s infinite; + animation: shimmer 1.3s infinite; + } + + @-webkit-keyframes shimmer { + 0% { + transform: translateX(-100%); + } + + 100% { + transform: translateX(100%); + } + } + + @keyframes shimmer { + 0% { + transform: translateX(-100%); + } + + 100% { + transform: translateX(100%); + } + } +} + +.embed-video { + width: 100%; + height: 100%; + margin-bottom: 1rem; + aspect-ratio: 16 / 9; + + @extend %rounded; + + &.twitch { + aspect-ratio: 310 / 189; + } + + &.file { + display: block; + width: auto; + height: auto; + max-width: 100%; + max-height: 100%; + margin: auto; + margin-bottom: 0; + } + + @extend %img-caption; +} + +.embed-audio { + width: 100%; + display: block; + + @extend %img-caption; +} + +/* --- buttons --- */ +.btn-lang { + border: 1px solid !important; + padding: 1px 3px; + border-radius: 3px; + color: var(--link-color); + + &:focus { + box-shadow: none; + } +} + +/* --- Effects classes --- */ + +.flex-grow-1 { + flex-grow: 1 !important; +} + +.btn-box-shadow { + box-shadow: var(--card-shadow); +} + +/* overwrite bootstrap muted */ +.text-muted { + color: var(--text-muted-color) !important; +} + +/* Overwrite bootstrap tooltip */ +.tooltip-inner { + font-size: 0.7rem; + max-width: 220px; + text-align: left; +} + +/* Overwrite bootstrap outline button */ +.btn.btn-outline-primary { + &:not(.disabled):hover { + border-color: #007bff !important; + } +} + +.disabled { + color: rgb(206, 196, 196); + pointer-events: auto; + cursor: not-allowed; +} + +.hide-border-bottom { + border-bottom: none !important; +} + +.input-focus { + box-shadow: none; + border-color: var(--input-focus-border-color) !important; + background: center !important; + transition: background-color 0.15s ease-in-out, border-color 0.15s ease-in-out; +} + +.left { + float: left; + margin: 0.75rem 1rem 1rem 0; +} + +.right { + float: right; + margin: 0.75rem 0 1rem 1rem; +} + +/* --- Overriding --- */ + +/* mermaid */ +.mermaid { + text-align: center; +} + +/* MathJax */ +mjx-container { + overflow-y: hidden; + min-width: auto !important; +} + +/* --- sidebar layout --- */ + +$sidebar-display: 'sidebar-display'; +$btn-border-width: 3px; +$btn-mb: 0.5rem; + +#sidebar { + @include pl-pr(0); + + position: fixed; + top: 0; + left: 0; + height: 100%; + overflow-y: auto; + width: $sidebar-width; + z-index: 99; + background: var(--sidebar-bg); + border-right: 1px solid var(--sidebar-border-color); + + /* Hide scrollbar for IE, Edge and Firefox */ + -ms-overflow-style: none; /* IE and Edge */ + scrollbar-width: none; /* Firefox */ + + /* Hide scrollbar for Chrome, Safari and Opera */ + &::-webkit-scrollbar { + display: none; + } + + %sidebar-link-hover { + &:hover { + color: var(--sidebar-active-color); + } + } + + a { + @extend %sidebar-links; + } + + #avatar { + display: block; + width: 7rem; + height: 7rem; + overflow: hidden; + box-shadow: var(--avatar-border-color) 0 0 0 2px; + transform: translateZ(0); /* fixed the zoom in Safari */ + + img { + transition: transform 0.5s; + + &:hover { + transform: scale(1.2); + } + } + } + + .profile-wrapper { + @include mt-mb(2.5rem); + @extend %clickable-transition; + + padding-left: 2.5rem; + padding-right: 1.25rem; + width: 100%; + } + + .site-title { + font-family: inherit; + font-weight: 900; + font-size: 1.75rem; + line-height: 1.2; + letter-spacing: 0.25px; + margin-top: 1.25rem; + margin-bottom: 0.5rem; + + a { + @extend %clickable-transition; + @extend %sidebar-link-hover; + + color: var(--site-title-color); + } + } + + .site-subtitle { + font-size: 95%; + color: var(--site-subtitle-color); + margin-top: 0.25rem; + word-spacing: 1px; + -webkit-user-select: none; + -moz-user-select: none; + -ms-user-select: none; + user-select: none; + } + + ul { + margin-bottom: 2rem; + + li.nav-item { + opacity: 0.9; + width: 100%; + padding-left: 1.5rem; + padding-right: 1.5rem; + + a.nav-link { + @include pt-pb(0.6rem); + + display: flex; + align-items: center; + border-radius: 0.75rem; + font-weight: 600; + + &:hover { + background-color: var(--sidebar-hover-bg); + } + + i { + font-size: 95%; + opacity: 0.8; + margin-right: 1.5rem; + } + + span { + font-size: 90%; + letter-spacing: 0.2px; + } + } + + &.active { + .nav-link { + color: var(--sidebar-active-color); + background-color: var(--sidebar-hover-bg); + + span { + opacity: 1; + } + } + } + + &:not(:first-child) { + margin-top: 0.25rem; + } + } + } + + .sidebar-bottom { + padding-left: 2rem; + padding-right: 1rem; + margin-bottom: 1.5rem; + + $btn-size: 1.75rem; + + %button { + width: $btn-size; + height: $btn-size; + margin-bottom: $btn-mb; // multi line gap + border-radius: 50%; + color: var(--sidebar-btn-color); + background-color: var(--sidebar-btn-bg); + text-align: center; + display: flex; + align-items: center; + justify-content: center; + + &:not(:focus-visible) { + box-shadow: var(--sidebar-border-color) 0 0 0 1px; + } + + &:hover { + background-color: var(--sidebar-hover-bg); + } + } + + a { + @extend %button; + @extend %sidebar-link-hover; + @extend %clickable-transition; + + &:not(:last-child) { + margin-right: $sb-btn-gap; + } + } + + i { + line-height: $btn-size; + } + + #mode-toggle { + @extend %button; + @extend %sidebar-links; + @extend %sidebar-link-hover; + } + + .icon-border { + @extend %no-cursor; + @include ml-mr(calc(($sb-btn-gap - $btn-border-width) / 2)); + + background-color: var(--sidebar-btn-color); + content: ''; + width: $btn-border-width; + height: $btn-border-width; + border-radius: 50%; + margin-bottom: $btn-mb; + } + } /* .sidebar-bottom */ +} /* #sidebar */ + +@media (hover: hover) { + #sidebar ul > li:last-child::after { + transition: top 0.5s ease; + } + + .nav-link { + transition: background-color 0.3s ease-in-out; + } + + .post-preview { + transition: background-color 0.35s ease-in-out; + } +} + +#search-result-wrapper { + display: none; + height: 100%; + width: 100%; + overflow: auto; + + .content { + margin-top: 2rem; + } +} + +/* --- top-bar --- */ + +#topbar-wrapper { + height: $topbar-height; + background-color: var(--topbar-bg); +} + +#topbar { + button i { + color: #999999; + } + + #breadcrumb { + font-size: 1rem; + color: var(--text-muted-color); + padding-left: 0.5rem; + + a:hover { + @extend %link-hover; + } + + span { + &:not(:last-child) { + &::after { + content: '›'; + padding: 0 0.3rem; + } + } + } + } +} /* #topbar */ + +::-webkit-input-placeholder { + @include placeholder; +} + +::-moz-placeholder { + @include placeholder; +} + +:-ms-input-placeholder { + @include placeholder; +} + +::-ms-input-placeholder { + @include placeholder; +} + +::placeholder { + @include placeholder; +} + +:focus::-webkit-input-placeholder { + @include placeholder-focus; +} + +:focus::-moz-placeholder { + @include placeholder-focus; +} + +:focus:-ms-input-placeholder { + @include placeholder-focus; +} + +:focus::-ms-input-placeholder { + @include placeholder-focus; +} + +:focus::placeholder { + @include placeholder-focus; +} + +search { + display: flex; + width: 100%; + border-radius: 1rem; + border: 1px solid var(--search-border-color); + background: var(--main-bg); + padding: 0 0.5rem; + + i { + z-index: 2; + font-size: 0.9rem; + color: var(--search-icon-color); + } +} + +#sidebar-trigger, +#search-trigger { + display: none; +} + +/* 'Cancel' link */ +#search-cancel { + color: var(--link-color); + display: none; + white-space: nowrap; + + @extend %cursor-pointer; +} + +#search-input { + background: center; + border: 0; + border-radius: 0; + padding: 0.18rem 0.3rem; + color: var(--text-color); + height: auto; + + &:focus { + box-shadow: none; + } +} + +#search-hints { + padding: 0 1rem; + + h4 { + margin-bottom: 1.5rem; + } + + .post-tag { + display: inline-block; + line-height: 1rem; + font-size: 1rem; + background: var(--search-tag-bg); + border: none; + padding: 0.5rem; + margin: 0 1.25rem 1rem 0; + + &::before { + content: '#'; + color: var(--text-muted-color); + padding-right: 0.2rem; + } + + @extend %link-color; + } +} + +#search-results { + padding-bottom: 3rem; + + a { + font-size: 1.4rem; + line-height: 2.5rem; + + &:hover { + @extend %link-hover; + } + + @extend %link-color; + @extend %no-bottom-border; + @extend %heading; + } + + > article { + width: 100%; + + &:not(:last-child) { + margin-bottom: 1rem; + } + + /* icons */ + i { + color: #818182; + margin-right: 0.15rem; + font-size: 80%; + } + + > p { + overflow: hidden; + text-overflow: ellipsis; + display: -webkit-box; + -webkit-line-clamp: 3; + -webkit-box-orient: vertical; + } + } +} /* #search-results */ + +#topbar-title { + display: none; + font-size: 1.1rem; + font-weight: 600; + font-family: sans-serif; + color: var(--topbar-text-color); + text-align: center; + width: 70%; + overflow: hidden; + text-overflow: ellipsis; + word-break: keep-all; + white-space: nowrap; +} + +#mask { + display: none; + position: fixed; + inset: 0 0 0 0; + height: 100%; + width: 100%; + z-index: 1; + + @at-root [#{$sidebar-display}] & { + display: block !important; + } +} + +/* --- basic wrappers --- */ + +#main-wrapper { + position: relative; + + @include pl-pr(0); + + > .container { + min-height: 100vh; + } +} + +#topbar-wrapper.row, +#main-wrapper > .container > .row, +#search-result-wrapper > .row { + @include ml-mr(0); +} + +#tail-wrapper { + > :not(script) { + margin-top: 3rem; + } +} + +/* --- button back-to-top --- */ + +#back-to-top { + visibility: hidden; + opacity: 0; + z-index: 1; + cursor: pointer; + position: fixed; + right: 1rem; + bottom: calc($footer-height-large - $back2top-size / 2); + background: var(--button-bg); + color: var(--btn-backtotop-color); + padding: 0; + width: $back2top-size; + height: $back2top-size; + border-radius: 50%; + border: 1px solid var(--btn-backtotop-border-color); + transition: opacity 0.5s ease-in-out, transform 0.2s ease-out; + + &:hover { + transform: translate3d(0, -5px, 0); + -webkit-transform: translate3d(0, -5px, 0); + } + + i { + line-height: $back2top-size; + position: relative; + bottom: 2px; + } + + &.show { + opacity: 1; + visibility: visible; + } +} + +#notification { + @-webkit-keyframes popup { + from { + opacity: 0; + bottom: 0; + } + } + + @keyframes popup { + from { + opacity: 0; + bottom: 0; + } + } + + .toast-header { + background: none; + border-bottom: none; + color: inherit; + } + + .toast-body { + font-family: Lato, sans-serif; + line-height: 1.25rem; + + button { + font-size: 90%; + min-width: 4rem; + } + } + + &.toast { + &.show { + display: block; + min-width: 20rem; + border-radius: 0.5rem; + -webkit-backdrop-filter: blur(10px); + backdrop-filter: blur(10px); + background-color: rgba(255, 255, 255, 0.5); + color: #1b1b1eba; + position: fixed; + left: 50%; + bottom: 20%; + transform: translateX(-50%); + -webkit-animation: popup 0.8s; + animation: popup 0.8s; + } + } +} + +/* + Responsive Design: + + {sidebar, content, panel} >= 1200px screen width + {sidebar, content} >= 850px screen width + {content} <= 849px screen width + +*/ + +@media all and (max-width: 576px) { + main { + .content { + > blockquote[class^='prompt-'] { + @include ml-mr(-1rem); + + border-radius: 0; + max-width: none; + } + } + } + + #avatar { + width: 5rem; + height: 5rem; + } +} + +@media all and (max-width: 768px) { + %full-width { + max-width: 100%; + } + + #topbar { + @extend %full-width; + } + + #main-wrapper > .container { + @extend %full-width; + @include pl-pr(0); + } +} + +/* hide sidebar and panel */ +@media all and (max-width: 849px) { + @mixin slide($append: null) { + $basic: transform 0.4s ease; + + @if $append { + transition: $basic, $append; + } @else { + transition: $basic; + } + } + + footer { + @include slide; + + height: $footer-height-large; + padding: 1.5rem 0; + } + + [#{$sidebar-display}] { + #sidebar { + transform: translateX(0); + } + + #main-wrapper { + transform: translateX($sidebar-width); + } + + #back-to-top { + visibility: hidden; + } + } + + #sidebar { + @include slide; + + transform: translateX(-$sidebar-width); /* hide */ + -webkit-transform: translateX(-$sidebar-width); + } + + #main-wrapper { + @include slide; + } + + #topbar, + #main-wrapper > .container { + max-width: 100%; + } + + #search-result-wrapper { + width: 100%; + } + + #breadcrumb, + search { + display: none; + } + + #topbar-wrapper { + @include slide(top 0.2s ease); + + left: 0; + } + + main, + #panel-wrapper { + margin-top: 0; + } + + #topbar-title, + #sidebar-trigger, + #search-trigger { + display: block; + } + + #search-result-wrapper .content { + letter-spacing: 0; + } + + #tags { + justify-content: center !important; + } + + h1.dynamic-title { + display: none; + + ~ .content { + margin-top: 2.5rem; + } + } +} /* max-width: 849px */ + +/* Sidebar is visible */ +@media all and (min-width: 850px) { + /* Solved jumping scrollbar */ + html { + overflow-y: scroll; + } + + #main-wrapper { + margin-left: $sidebar-width; + } + + #sidebar { + .profile-wrapper { + margin-top: 3rem; + } + } + + #search-hints { + display: none; + } + + search { + max-width: $search-max-width; + } + + #search-result-wrapper { + max-width: $main-content-max-width; + justify-content: start !important; + } + + main { + h1 { + margin-top: 3rem; + } + } + + div.content .table-wrapper > table { + min-width: 70%; + } + + /* button 'back-to-Top' position */ + #back-to-top { + right: 5%; + bottom: calc($footer-height - $back2top-size / 2); + } + + #topbar-title { + text-align: left; + } +} + +/* Pad horizontal */ +@media all and (min-width: 992px) and (max-width: 1199px) { + #main-wrapper > .container .col-lg-11 { + flex: 0 0 96%; + max-width: 96%; + } +} + +/* Compact icons in sidebar & panel hidden */ +@media all and (min-width: 850px) and (max-width: 1199px) { + #search-results > div { + max-width: 700px; + } + + #breadcrumb { + width: 65%; + overflow: hidden; + text-overflow: ellipsis; + word-break: keep-all; + white-space: nowrap; + } +} + +/* panel hidden */ +@media all and (max-width: 1199px) { + #panel-wrapper { + display: none; + } + + #main-wrapper > .container > div.row { + justify-content: center !important; + } +} + +/* --- desktop mode, both sidebar and panel are visible --- */ + +@media all and (min-width: 1200px) { + search { + margin-right: 4rem; + } + + #search-input { + transition: all 0.3s ease-in-out; + } + + #search-results > article { + width: 45%; + + &:nth-child(odd) { + margin-right: 1.5rem; + } + + &:nth-child(even) { + margin-left: 1.5rem; + } + + &:last-child:nth-child(odd) { + position: relative; + right: 24.3%; + } + } + + .content { + font-size: 1.03rem; + } +} + +@media all and (min-width: 1400px) { + #back-to-top { + right: calc((100vw - $sidebar-width - 1140px) / 2 + 3rem); + } +} + +@media all and (min-width: 1650px) { + $icon-gap: 1rem; + + #main-wrapper { + margin-left: $sidebar-width-large; + } + + #topbar-wrapper { + left: $sidebar-width-large; + } + + search { + margin-right: calc( + $main-content-max-width / 4 - $search-max-width - 0.75rem + ); + } + + #main-wrapper > .container { + max-width: $main-content-max-width; + padding-left: 1.75rem !important; + padding-right: 1.75rem !important; + } + + main.col-12, + #tail-wrapper { + padding-right: 4.5rem !important; + } + + #back-to-top { + right: calc( + (100vw - $sidebar-width-large - $main-content-max-width) / 2 + 2rem + ); + } + + #sidebar { + width: $sidebar-width-large; + + .profile-wrapper { + margin-top: 3.5rem; + margin-bottom: 2.5rem; + padding-left: 3.5rem; + } + + ul { + li.nav-item { + @include pl-pr(2.75rem); + } + } + + .sidebar-bottom { + padding-left: 2.75rem; + margin-bottom: 1.75rem; + + a:not(:last-child) { + margin-right: $sb-btn-gap-lg; + } + + .icon-border { + @include ml-mr(calc(($sb-btn-gap-lg - $btn-border-width) / 2)); + } + } + } +} /* min-width: 1650px */ diff --git a/_sass/addon/module.scss b/_sass/addon/module.scss new file mode 100644 index 0000000..9e85adc --- /dev/null +++ b/_sass/addon/module.scss @@ -0,0 +1,204 @@ +/* +* Mainly scss modules, only imported to `assets/css/main.scss` +*/ + +/* ---------- scss placeholder --------- */ + +%heading { + color: var(--heading-color); + font-weight: 400; + font-family: $font-family-heading; +} + +%section { + main & { + margin-top: 2.5rem; + margin-bottom: 1.25rem; + + &:focus { + outline: none; /* avoid outline in Safari */ + } + } +} + +%anchor { + .anchor { + font-size: 80%; + } + + @media (hover: hover) { + .anchor { + visibility: hidden; + opacity: 0; + transition: opacity 0.25s ease-in, visibility 0s ease-in 0.25s; + } + + &:hover { + .anchor { + visibility: visible; + opacity: 1; + transition: opacity 0.25s ease-in, visibility 0s ease-in 0s; + } + } + } +} + +%tag-hover { + background: var(--tag-hover); + transition: background 0.35s ease-in-out; +} + +%table-cell { + padding: 0.4rem 1rem; + font-size: 95%; + white-space: nowrap; +} + +%link-hover { + color: #d2603a !important; + border-bottom: 1px solid #d2603a; + text-decoration: none; +} + +%link-color { + color: var(--link-color); +} + +%link-underline { + border-bottom: 1px solid var(--link-underline-color); +} + +%clickable-transition { + transition: all 0.3s ease-in-out; +} + +%no-cursor { + -webkit-user-select: none; + -moz-user-select: none; + -ms-user-select: none; + user-select: none; +} + +%no-bottom-border { + border-bottom: none; +} + +%cursor-pointer { + cursor: pointer; +} + +%normal-font-style { + font-style: normal; +} + +%rounded { + border-radius: $base-radius; +} + +%img-caption { + + em { + display: block; + text-align: center; + font-style: normal; + font-size: 80%; + padding: 0; + color: #6d6c6c; + } +} + +%sidebar-links { + color: var(--sidebar-muted-color); + -webkit-user-select: none; + -moz-user-select: none; + -ms-user-select: none; + user-select: none; +} + +%text-clip { + display: -webkit-box; + overflow: hidden; + text-overflow: ellipsis; + -webkit-line-clamp: 2; + -webkit-box-orient: vertical; +} + +%text-highlight { + color: var(--text-muted-highlight-color); + font-weight: 600; +} + +%text-sm { + font-size: 0.85rem; +} + +%text-xs { + font-size: 0.8rem; +} + +%sup-fn-target { + &:target { + background-color: var(--footnote-target-bg); + width: -moz-fit-content; + width: -webkit-fit-content; + width: fit-content; + transition: background-color 1.75s ease-in-out; + } +} + +/* ---------- scss mixin --------- */ + +@mixin mt-mb($value) { + margin-top: $value; + margin-bottom: $value; +} + +@mixin ml-mr($value) { + margin-left: $value; + margin-right: $value; +} + +@mixin pt-pb($val) { + padding-top: $val; + padding-bottom: $val; +} + +@mixin pl-pr($val) { + padding-left: $val; + padding-right: $val; +} + +@mixin placeholder { + color: var(--text-muted-color) !important; +} + +@mixin placeholder-focus { + opacity: 0.6; +} + +@mixin label($font-size: 1rem, $font-weight: 600, $color: var(--label-color)) { + color: $color; + font-size: $font-size; + font-weight: $font-weight; +} + +@mixin align-center { + position: relative; + left: 50%; + transform: translateX(-50%); +} + +@mixin prompt($type, $fa-content, $fa-style: 'solid', $rotate: 0) { + &.prompt-#{$type} { + background-color: var(--prompt-#{$type}-bg); + + &::before { + content: $fa-content; + color: var(--prompt-#{$type}-icon-color); + font: var(--fa-font-#{$fa-style}); + + @if $rotate != 0 { + transform: rotate(#{$rotate}deg); + } + } + } +} diff --git a/_sass/addon/syntax.scss b/_sass/addon/syntax.scss new file mode 100644 index 0000000..b0efd20 --- /dev/null +++ b/_sass/addon/syntax.scss @@ -0,0 +1,292 @@ +/* +* The syntax highlight. +*/ + +@import 'colors/syntax-light'; +@import 'colors/syntax-dark'; + +html { + @media (prefers-color-scheme: light) { + &:not([data-mode]), + &[data-mode='light'] { + @include light-syntax; + } + + &[data-mode='dark'] { + @include dark-syntax; + } + } + + @media (prefers-color-scheme: dark) { + &:not([data-mode]), + &[data-mode='dark'] { + @include dark-syntax; + } + + &[data-mode='light'] { + @include light-syntax; + } + } +} + +/* -- code snippets -- */ + +%code-snippet-bg { + background-color: var(--highlight-bg-color); +} + +%code-snippet-padding { + padding-left: 1rem; + padding-right: 1.5rem; +} + +.highlighter-rouge { + color: var(--highlighter-rouge-color); + margin-top: 0.5rem; + margin-bottom: 1.2em; /* Override BS Inline-code style */ +} + +.highlight { + @extend %rounded; + @extend %code-snippet-bg; + + overflow: auto; + padding-bottom: 0.75rem; + + @at-root figure#{&} { + @extend %code-snippet-bg; + } + + pre { + margin-bottom: 0; + font-size: $code-font-size; + line-height: 1.4rem; + word-wrap: normal; /* Fixed Safari overflow-x */ + } + + table { + td { + &:first-child { + display: inline-block; + margin-left: 1rem; + margin-right: 0.75rem; + } + + &:last-child { + padding-right: 2rem !important; + } + + pre { + overflow: visible; /* Fixed iOS safari overflow-x */ + word-break: normal; /* Fixed iOS safari linenos code break */ + } + } + } + + .lineno { + text-align: right; + color: var(--highlight-lineno-color); + -webkit-user-select: none; + -moz-user-select: none; + -o-user-select: none; + -ms-user-select: none; + user-select: none; + } +} /* .highlight */ + +code { + -webkit-hyphens: none; + -ms-hyphens: none; + hyphens: none; + color: var(--code-color); + + &.highlighter-rouge { + font-size: $code-font-size; + padding: 3px 6px; + word-break: break-word; + border-radius: 4px; + background-color: var(--inline-code-bg); + } + + &.filepath { + background-color: inherit; + color: var(--filepath-text-color); + font-weight: 600; + padding: 0; + } + + a > &.highlighter-rouge { + padding-bottom: 0; /* show link's underlinke */ + color: inherit; + } + + a:hover > &.highlighter-rouge { + border-bottom: none; + } + + blockquote & { + color: inherit; + } +} + +td.rouge-code { + @extend %code-snippet-padding; + + /* + Prevent some browser extends from + changing the URL string of code block. + */ + a { + color: inherit !important; + border-bottom: none !important; + pointer-events: none; + } +} + +div[class^='language-'] { + @extend %rounded; + @extend %code-snippet-bg; + + box-shadow: var(--language-border-color) 0 0 0 1px; + + .content > & { + @include ml-mr(-1rem); + + border-radius: 0; + } + + .highlight { + border-top-left-radius: 0; + border-top-right-radius: 0; + } +} + +/* Hide line numbers for default, console, and terminal code snippets */ +div { + &.nolineno, + &.language-plaintext, + &.language-console, + &.language-terminal { + td:first-child { + padding: 0 !important; + margin-right: 0; + + .lineno { + display: none; + } + } + } +} + +.code-header { + @extend %no-cursor; + + display: flex; + justify-content: space-between; + align-items: center; + height: $code-header-height; + margin-left: 0.75rem; + margin-right: 0.25rem; + + /* the label block */ + span { + line-height: $code-header-height; + + /* label icon */ + i { + font-size: 1rem; + width: $code-icon-width; + color: var(--code-header-icon-color); + + &.small { + font-size: 70%; + } + } + + @at-root [file] #{&} > i { + position: relative; + top: 1px; /* center the file icon */ + } + + /* label text */ + &::after { + content: attr(data-label-text); + font-size: 0.85rem; + font-weight: 600; + color: var(--code-header-text-color); + } + } + + /* clipboard */ + button { + @extend %cursor-pointer; + @extend %rounded; + + border: 1px solid transparent; + height: $code-header-height; + width: $code-header-height; + padding: 0; + background-color: inherit; + + i { + color: var(--code-header-icon-color); + } + + &[timeout] { + &:hover { + border-color: var(--clipboard-checked-color); + } + + i { + color: var(--clipboard-checked-color); + } + } + + &:focus { + outline: none; + } + + &:not([timeout]):hover { + background-color: rgba(128, 128, 128, 0.37); + + i { + color: white; + } + } + } +} + +@media all and (min-width: 576px) { + div[class^='language-'] { + .content > & { + @include ml-mr(0); + + border-radius: $base-radius; + } + + .code-header { + @include ml-mr(0); + + $dot-margin: 1rem; + + &::before { + content: ''; + display: inline-block; + margin-left: $dot-margin; + width: $code-dot-size; + height: $code-dot-size; + border-radius: 50%; + background-color: var(--code-header-muted-color); + box-shadow: ($code-dot-size + $code-dot-gap) 0 0 + var(--code-header-muted-color), + ($code-dot-size + $code-dot-gap) * 2 0 0 + var(--code-header-muted-color); + } + + span { + // center the text of label + margin-left: calc(($dot-margin + $code-dot-size) / 2 * -1); + } + } + } +} diff --git a/_sass/addon/variables.scss b/_sass/addon/variables.scss new file mode 100644 index 0000000..8924a00 --- /dev/null +++ b/_sass/addon/variables.scss @@ -0,0 +1,33 @@ +/* + * The SCSS variables + */ + +/* sidebar */ + +$sidebar-width: 260px !default; /* the basic width */ +$sidebar-width-large: 300px !default; /* screen width: >= 1650px */ +$sb-btn-gap: 0.8rem !default; +$sb-btn-gap-lg: 1rem !default; + +/* other framework sizes */ + +$topbar-height: 3rem !default; +$search-max-width: 200px !default; +$footer-height: 5rem !default; +$footer-height-large: 6rem !default; /* screen width: < 850px */ +$main-content-max-width: 1250px !default; +$base-radius: 0.625rem !default; +$back2top-size: 2.75rem !default; + +/* syntax highlight */ + +$code-font-size: 0.85rem !default; +$code-header-height: 2.25rem !default; +$code-dot-size: 0.75rem !default; +$code-dot-gap: 0.5rem !default; +$code-icon-width: 1.75rem !default; + +/* fonts */ + +$font-family-base: 'Source Sans Pro', 'Microsoft Yahei', sans-serif !default; +$font-family-heading: Lato, 'Microsoft Yahei', sans-serif !default; diff --git a/_sass/colors/syntax-dark.scss b/_sass/colors/syntax-dark.scss new file mode 100644 index 0000000..eb92204 --- /dev/null +++ b/_sass/colors/syntax-dark.scss @@ -0,0 +1,164 @@ +/* + * The syntax dark mode styles. + */ + +@mixin dark-syntax { + --language-border-color: #2d2d2d; + --highlight-bg-color: #151515; + --highlighter-rouge-color: #c9def1; + --highlight-lineno-color: #808080; + --inline-code-bg: rgba(255, 255, 255, 0.05); + --code-color: #b0b0b0; + --code-header-text-color: #6a6a6a; + --code-header-muted-color: #353535; + --code-header-icon-color: #565656; + --clipboard-checked-color: #2bcc2b; + --filepath-text-color: #cacaca; + + .highlight .gp { + color: #87939d; + } + + /* --- Syntax highlight theme from `rougify style base16.dark` --- */ + + .highlight table td { + padding: 5px; + } + + .highlight table pre { + margin: 0; + } + + .highlight, + .highlight .w { + color: #d0d0d0; + background-color: #151515; + } + + .highlight .err { + color: #151515; + background-color: #ac4142; + } + + .highlight .c, + .highlight .ch, + .highlight .cd, + .highlight .cm, + .highlight .cpf, + .highlight .c1, + .highlight .cs { + color: #848484; + } + + .highlight .cp { + color: #f4bf75; + } + + .highlight .nt { + color: #f4bf75; + } + + .highlight .o, + .highlight .ow { + color: #d0d0d0; + } + + .highlight .p, + .highlight .pi { + color: #d0d0d0; + } + + .highlight .gi { + color: #90a959; + } + + .highlight .gd { + color: #f08a8b; + background-color: #320000; + } + + .highlight .gh { + color: #6a9fb5; + background-color: #151515; + font-weight: bold; + } + + .highlight .k, + .highlight .kn, + .highlight .kp, + .highlight .kr, + .highlight .kv { + color: #aa759f; + } + + .highlight .kc { + color: #d28445; + } + + .highlight .kt { + color: #d28445; + } + + .highlight .kd { + color: #d28445; + } + + .highlight .s, + .highlight .sb, + .highlight .sc, + .highlight .dl, + .highlight .sd, + .highlight .s2, + .highlight .sh, + .highlight .sx, + .highlight .s1 { + color: #90a959; + } + + .highlight .sa { + color: #aa759f; + } + + .highlight .sr { + color: #75b5aa; + } + + .highlight .si { + color: #b76d45; + } + + .highlight .se { + color: #b76d45; + } + + .highlight .nn { + color: #f4bf75; + } + + .highlight .nc { + color: #f4bf75; + } + + .highlight .no { + color: #f4bf75; + } + + .highlight .na { + color: #6a9fb5; + } + + .highlight .m, + .highlight .mb, + .highlight .mf, + .highlight .mh, + .highlight .mi, + .highlight .il, + .highlight .mo, + .highlight .mx { + color: #90a959; + } + + .highlight .ss { + color: #90a959; + } +} diff --git a/_sass/colors/syntax-light.scss b/_sass/colors/syntax-light.scss new file mode 100644 index 0000000..76aa669 --- /dev/null +++ b/_sass/colors/syntax-light.scss @@ -0,0 +1,210 @@ +/* + * The syntax light mode code snippet colors. + */ + +@mixin light-syntax { + /* --- custom light colors --- */ + --language-border-color: #ececec; + --highlight-bg-color: #f6f8fa; + --highlighter-rouge-color: #3f596f; + --highlight-lineno-color: #9e9e9e; + --inline-code-bg: rgba(25, 25, 28, 0.05); + --code-color: #3a3a3a; + --code-header-text-color: #a3a3a3; + --code-header-muted-color: #e5e5e5; + --code-header-icon-color: #c9c8c8; + --clipboard-checked-color: #43c743; + + /* --- Syntax highlight theme from `rougify style github` --- */ + + .highlight table td { + padding: 5px; + } + + .highlight table pre { + margin: 0; + } + + .highlight, + .highlight .w { + color: #24292f; + background-color: #f6f8fa; + } + + .highlight .k, + .highlight .kd, + .highlight .kn, + .highlight .kp, + .highlight .kr, + .highlight .kt, + .highlight .kv { + color: #cf222e; + } + + .highlight .gr { + color: #f6f8fa; + } + + .highlight .gd { + color: #82071e; + background-color: #ffebe9; + } + + .highlight .nb { + color: #953800; + } + + .highlight .nc { + color: #953800; + } + + .highlight .no { + color: #953800; + } + + .highlight .nn { + color: #953800; + } + + .highlight .sr { + color: #116329; + } + + .highlight .na { + color: #116329; + } + + .highlight .nt { + color: #116329; + } + + .highlight .gi { + color: #116329; + background-color: #dafbe1; + } + + .highlight .kc { + color: #0550ae; + } + + .highlight .l, + .highlight .ld, + .highlight .m, + .highlight .mb, + .highlight .mf, + .highlight .mh, + .highlight .mi, + .highlight .il, + .highlight .mo, + .highlight .mx { + color: #0550ae; + } + + .highlight .sb { + color: #0550ae; + } + + .highlight .bp { + color: #0550ae; + } + + .highlight .ne { + color: #0550ae; + } + + .highlight .nl { + color: #0550ae; + } + + .highlight .py { + color: #0550ae; + } + + .highlight .nv, + .highlight .vc, + .highlight .vg, + .highlight .vi, + .highlight .vm { + color: #0550ae; + } + + .highlight .o, + .highlight .ow { + color: #0550ae; + } + + .highlight .gh { + color: #0550ae; + font-weight: bold; + } + + .highlight .gu { + color: #0550ae; + font-weight: bold; + } + + .highlight .s, + .highlight .sa, + .highlight .sc, + .highlight .dl, + .highlight .sd, + .highlight .s2, + .highlight .se, + .highlight .sh, + .highlight .sx, + .highlight .s1, + .highlight .ss { + color: #0a3069; + } + + .highlight .nd { + color: #8250df; + } + + .highlight .nf, + .highlight .fm { + color: #8250df; + } + + .highlight .err { + color: #f6f8fa; + background-color: #82071e; + } + + .highlight .c, + .highlight .ch, + .highlight .cd, + .highlight .cm, + .highlight .cp, + .highlight .cpf, + .highlight .c1, + .highlight .cs { + color: #68717a; + } + + .highlight .gl { + color: #68717a; + } + + .highlight .gt { + color: #68717a; + } + + .highlight .ni { + color: #24292f; + } + + .highlight .si { + color: #24292f; + } + + .highlight .ge { + color: #24292f; + font-style: italic; + } + + .highlight .gs { + color: #24292f; + font-weight: bold; + } +} /* light-syntax */ diff --git a/_sass/colors/typography-dark.scss b/_sass/colors/typography-dark.scss new file mode 100644 index 0000000..12427ec --- /dev/null +++ b/_sass/colors/typography-dark.scss @@ -0,0 +1,147 @@ +/* + * The main dark mode styles + */ + +@mixin dark-scheme { + /* Framework color */ + --main-bg: rgb(27, 27, 30); + --mask-bg: rgb(68, 69, 70); + --main-border-color: rgb(44, 45, 45); + + /* Common color */ + --text-color: rgb(175, 176, 177); + --text-muted-color: #868686; + --text-muted-highlight-color: #aeaeae; + --heading-color: #cccccc; + --label-color: #a7a7a7; + --blockquote-border-color: rgb(66, 66, 66); + --blockquote-text-color: #868686; + --link-color: rgb(138, 180, 248); + --link-underline-color: rgb(82, 108, 150); + --button-bg: #1e1e1e; + --btn-border-color: #2e2f31; + --btn-backtotop-color: var(--text-color); + --btn-backtotop-border-color: #212122; + --btn-box-shadow: var(--main-bg); + --card-header-bg: #292929; + --checkbox-color: rgb(118, 120, 121); + --checkbox-checked-color: var(--link-color); + --img-bg: radial-gradient(circle, rgb(22, 22, 24) 0%, rgb(32, 32, 32) 100%); + --shimmer-bg: linear-gradient( + 90deg, + rgba(255, 255, 255, 0) 0%, + rgba(58, 55, 55, 0.4) 50%, + rgba(255, 255, 255, 0) 100% + ); + + /* Sidebar */ + --site-title-color: #717070; + --site-subtitle-color: #868686; + --sidebar-bg: #1e1e1e; + --sidebar-border-color: #292929; + --sidebar-muted-color: #868686; + --sidebar-active-color: rgb(255, 255, 255, 0.95); + --sidebar-hover-bg: #262626; + --sidebar-btn-bg: #232328; + --sidebar-btn-color: #787878; + --avatar-border-color: rgb(206, 206, 206, 0.9); + + /* Topbar */ + --topbar-bg: rgb(27, 27, 30, 0.64); + --topbar-text-color: var(--text-color); + --search-border-color: rgb(55, 55, 55); + --search-icon-color: rgb(100, 102, 105); + --input-focus-border-color: rgb(112, 114, 115); + + /* Home page */ + --post-list-text-color: rgb(175, 176, 177); + --btn-patinator-text-color: var(--text-color); + --btn-paginator-hover-color: #2e2e2e; + + /* Posts */ + --toc-highlight: rgb(116, 178, 243); + --tag-hover: rgb(43, 56, 62); + --tb-odd-bg: #252526; /* odd rows of the posts' table */ + --tb-even-bg: rgb(31, 31, 34); /* even rows of the posts' table */ + --tb-border-color: var(--tb-odd-bg); + --footnote-target-bg: rgb(63, 81, 181); + --btn-share-color: #6c757d; + --btn-share-hover-color: #bfc1ca; + --card-bg: #1e1e1e; + --card-hovor-bg: #464d51; + --card-shadow: rgb(21, 21, 21, 0.72) 0 6px 18px 0, + rgb(137, 135, 135, 0.24) 0 0 0 1px; + --kbd-wrap-color: #6a6a6a; + --kbd-text-color: #d3d3d3; + --kbd-bg-color: #242424; + --prompt-text-color: rgb(216, 212, 212, 0.75); + --prompt-tip-bg: rgb(22, 60, 36, 0.64); + --prompt-tip-icon-color: rgb(15, 164, 15, 0.81); + --prompt-info-bg: rgb(7, 59, 104, 0.8); + --prompt-info-icon-color: #0075d1; + --prompt-warning-bg: rgb(90, 69, 3, 0.88); + --prompt-warning-icon-color: rgb(255, 165, 0, 0.8); + --prompt-danger-bg: rgb(86, 28, 8, 0.8); + --prompt-danger-icon-color: #cd0202; + + /* Tags */ + --tag-border: rgb(59, 79, 88); + --tag-shadow: rgb(32, 33, 33); + --dash-color: rgb(63, 65, 68); + --search-tag-bg: #292828; + + /* Categories */ + --categories-border: rgb(64, 66, 69, 0.5); + --categories-hover-bg: rgb(73, 75, 76); + --categories-icon-hover-color: white; + + /* Archive */ + --timeline-node-bg: rgb(150, 152, 156); + --timeline-color: rgb(63, 65, 68); + --timeline-year-dot-color: var(--timeline-color); + + color-scheme: dark; + + .light { + display: none; + } + + /* Categories */ + .categories.card, + .list-group-item { + background-color: var(--card-bg); + } + + .categories { + .card-header { + background-color: var(--card-header-bg); + } + + .list-group-item { + border-left: none; + border-right: none; + padding-left: 2rem; + border-color: var(--categories-border); + + &:last-child { + border-bottom-color: var(--card-bg); + } + } + } + + #archives li:nth-child(odd) { + background-image: linear-gradient( + to left, + rgb(26, 26, 30), + rgb(39, 39, 45), + rgb(39, 39, 45), + rgb(39, 39, 45), + rgb(26, 26, 30) + ); + } + + /* stylelint-disable-next-line selector-id-pattern */ + #disqus_thread { + color-scheme: none; + } +} /* dark-scheme */ diff --git a/_sass/colors/typography-light.scss b/_sass/colors/typography-light.scss new file mode 100644 index 0000000..7800074 --- /dev/null +++ b/_sass/colors/typography-light.scss @@ -0,0 +1,112 @@ +/* + * The syntax light mode typography colors + */ + +@mixin light-scheme { + /* Framework color */ + --main-bg: white; + --mask-bg: #c1c3c5; + --main-border-color: #f3f3f3; + + /* Common color */ + --text-color: #34343c; + --text-muted-color: #757575; + --text-muted-highlight-color: inherit; + --heading-color: #2a2a2a; + --label-color: #585858; + --blockquote-border-color: #eeeeee; + --blockquote-text-color: #757575; + --link-color: #0056b2; + --link-underline-color: #dee2e6; + --button-bg: #ffffff; + --btn-border-color: #e9ecef; + --btn-backtotop-color: #686868; + --btn-backtotop-border-color: #f1f1f1; + --btn-box-shadow: #eaeaea; + --checkbox-color: #c5c5c5; + --checkbox-checked-color: #07a8f7; + --img-bg: radial-gradient( + circle, + rgb(255, 255, 255) 0%, + rgb(239, 239, 239) 100% + ); + --shimmer-bg: linear-gradient( + 90deg, + rgba(250, 250, 250, 0) 0%, + rgba(232, 230, 230, 1) 50%, + rgba(250, 250, 250, 0) 100% + ); + + /* Sidebar */ + --site-title-color: rgb(113, 113, 113); + --site-subtitle-color: #717171; + --sidebar-bg: #f6f8fa; + --sidebar-border-color: #efefef; + --sidebar-muted-color: #545454; + --sidebar-active-color: #1d1d1d; + --sidebar-hover-bg: rgb(223, 233, 241, 0.64); + --sidebar-btn-bg: white; + --sidebar-btn-color: #8e8e8e; + --avatar-border-color: white; + + /* Topbar */ + --topbar-bg: rgb(255, 255, 255, 0.7); + --topbar-text-color: rgb(78, 78, 78); + --search-border-color: rgb(240, 240, 240); + --search-icon-color: #c2c6cc; + --input-focus-border-color: #b8b8b8; + + /* Home page */ + --post-list-text-color: dimgray; + --btn-patinator-text-color: #555555; + --btn-paginator-hover-color: var(--sidebar-bg); + + /* Posts */ + --toc-highlight: #0550ae; + --btn-share-color: gray; + --btn-share-hover-color: #0d6efd; + --card-bg: white; + --card-hovor-bg: #e2e2e2; + --card-shadow: rgb(104, 104, 104, 0.05) 0 2px 6px 0, + rgba(211, 209, 209, 0.15) 0 0 0 1px; + --footnote-target-bg: lightcyan; + --tb-odd-bg: #fbfcfd; + --tb-border-color: #eaeaea; + --dash-color: silver; + --kbd-wrap-color: #bdbdbd; + --kbd-text-color: var(--text-color); + --kbd-bg-color: white; + --prompt-text-color: rgb(46, 46, 46, 0.77); + --prompt-tip-bg: rgb(123, 247, 144, 0.2); + --prompt-tip-icon-color: #03b303; + --prompt-info-bg: #e1f5fe; + --prompt-info-icon-color: #0070cb; + --prompt-warning-bg: rgb(255, 243, 205); + --prompt-warning-icon-color: #ef9c03; + --prompt-danger-bg: rgb(248, 215, 218, 0.56); + --prompt-danger-icon-color: #df3c30; + + /* Tags */ + --tag-border: #dee2e6; + --tag-shadow: var(--btn-border-color); + --tag-hover: rgb(222, 226, 230); + --search-tag-bg: #f8f9fa; + + /* Categories */ + --categories-border: rgba(0, 0, 0, 0.125); + --categories-hover-bg: var(--btn-border-color); + --categories-icon-hover-color: darkslategray; + + /* Archive */ + --timeline-color: rgba(0, 0, 0, 0.075); + --timeline-node-bg: #c2c6cc; + --timeline-year-dot-color: #ffffff; + + [class^='prompt-'] { + --link-underline-color: rgb(219, 216, 216); + } + + .dark { + display: none; + } +} /* light-scheme */ diff --git a/_sass/layout/archives.scss b/_sass/layout/archives.scss new file mode 100644 index 0000000..3a2e86b --- /dev/null +++ b/_sass/layout/archives.scss @@ -0,0 +1,144 @@ +/* + Style for Archives +*/ + +#archives { + letter-spacing: 0.03rem; + + $timeline-width: 4px; + + %timeline { + content: ''; + width: $timeline-width; + position: relative; + float: left; + background-color: var(--timeline-color); + } + + .year { + height: 3.5rem; + font-size: 1.5rem; + position: relative; + left: 2px; + margin-left: -$timeline-width; + + &::before { + @extend %timeline; + + height: 72px; + left: 79px; + bottom: 16px; + } + + &:first-child::before { + @extend %timeline; + + height: 32px; + top: 24px; + } + + /* Year dot */ + &::after { + content: ''; + display: inline-block; + position: relative; + border-radius: 50%; + width: 12px; + height: 12px; + left: 21.5px; + border: 3px solid; + background-color: var(--timeline-year-dot-color); + border-color: var(--timeline-node-bg); + box-shadow: 0 0 2px 0 #c2c6cc; + z-index: 1; + } + } + + ul { + li { + font-size: 1.1rem; + line-height: 3rem; + white-space: nowrap; + overflow: hidden; + text-overflow: ellipsis; + + &:nth-child(odd) { + background-color: var(--main-bg, #ffffff); + background-image: linear-gradient( + to left, + #ffffff, + #fbfbfb, + #fbfbfb, + #fbfbfb, + #ffffff + ); + } + + &::before { + @extend %timeline; + + top: 0; + left: 77px; + height: 3.1rem; + } + } + + &:last-child li:last-child::before { + height: 1.5rem; + } + } /* #archives ul */ + + .date { + white-space: nowrap; + display: inline-block; + position: relative; + right: 0.5rem; + + &.month { + width: 1.4rem; + text-align: center; + } + + &.day { + font-size: 85%; + font-family: Lato, sans-serif; + } + } + + a { + /* post title in Archvies */ + margin-left: 2.5rem; + position: relative; + top: 0.1rem; + + &:hover { + border-bottom: none; + } + + &::before { + /* the dot before post title */ + content: ''; + display: inline-block; + position: relative; + border-radius: 50%; + width: 8px; + height: 8px; + float: left; + top: 1.35rem; + left: 71px; + background-color: var(--timeline-node-bg); + box-shadow: 0 0 3px 0 #c2c6cc; + z-index: 1; + } + } +} /* #archives */ + +@media all and (max-width: 576px) { + #archives { + margin-top: -1rem; + + ul { + letter-spacing: 0; + } + } +} diff --git a/_sass/layout/categories.scss b/_sass/layout/categories.scss new file mode 100644 index 0000000..330d3d3 --- /dev/null +++ b/_sass/layout/categories.scss @@ -0,0 +1,83 @@ +/* + Style for Tab Categories +*/ + +%category-icon-color { + color: gray; +} + +.categories { + margin-bottom: 2rem; + border-color: var(--categories-border); + + &.card, + .list-group { + @extend %rounded; + } + + .card-header { + $radius: calc($base-radius - 1px); + + padding: 0.75rem; + border-radius: $radius; + border-bottom: 0; + + &.hide-border-bottom { + border-bottom-left-radius: 0; + border-bottom-right-radius: 0; + } + } + + i { + @extend %category-icon-color; + + font-size: 86%; /* fontawesome icons */ + } + + .list-group-item { + border-left: none; + border-right: none; + padding-left: 2rem; + + &:first-child { + border-top-left-radius: 0; + border-top-right-radius: 0; + } + + &:last-child { + border-bottom: 0; + } + } +} /* .categories */ + +.category-trigger { + width: 1.7rem; + height: 1.7rem; + border-radius: 50%; + text-align: center; + color: #6c757d !important; + + i { + position: relative; + height: 0.7rem; + width: 1rem; + transition: transform 300ms ease; + } + + &:hover { + i { + color: var(--categories-icon-hover-color); + } + } +} + +/* only works on desktop */ +@media (hover: hover) { + .category-trigger:hover { + background-color: var(--categories-hover-bg); + } +} + +.rotate { + transform: rotate(-90deg); +} diff --git a/_sass/layout/category-tag.scss b/_sass/layout/category-tag.scss new file mode 100644 index 0000000..9e43a91 --- /dev/null +++ b/_sass/layout/category-tag.scss @@ -0,0 +1,72 @@ +/* + Style for page Category and Tag +*/ + +.dash { + margin: 0 0.5rem 0.6rem 0.5rem; + border-bottom: 2px dotted var(--dash-color); +} + +#page-category, +#page-tag { + ul > li { + line-height: 1.5rem; + padding: 0.6rem 0; + + /* dot */ + &::before { + background: #999999; + width: 5px; + height: 5px; + border-radius: 50%; + display: block; + content: ''; + position: relative; + top: 0.6rem; + margin-right: 0.5rem; + } + + /* post's title */ + > a { + @extend %no-bottom-border; + + font-size: 1.1rem; + } + } +} + +/* tag icon */ +#page-tag h1 > i { + font-size: 1.2rem; +} + +#page-category h1 > i { + font-size: 1.25rem; +} + +#page-category, +#page-tag, +#access-lastmod { + a:hover { + @extend %link-hover; + + margin-bottom: -1px; /* Avoid jumping */ + } +} + +@media all and (max-width: 576px) { + #page-category, + #page-tag { + ul > li { + &::before { + margin: 0 0.5rem; + } + + > a { + white-space: nowrap; + overflow: hidden; + text-overflow: ellipsis; + } + } + } +} diff --git a/_sass/layout/home.scss b/_sass/layout/home.scss new file mode 100644 index 0000000..7f9fd2e --- /dev/null +++ b/_sass/layout/home.scss @@ -0,0 +1,189 @@ +/* + Style for Homepage +*/ + +#post-list { + margin-top: 2rem; + + .card-wrapper { + &:hover { + text-decoration: none; + } + + &:not(:last-child) { + margin-bottom: 1.25rem; + } + } + + .card { + border: 0; + background: none; + + %img-radius { + border-radius: $base-radius $base-radius 0 0; + } + + .preview-img { + @extend %img-radius; + + img { + @extend %img-radius; + } + } + + .card-body { + height: 100%; + padding: 1rem; + + .card-title { + @extend %text-clip; + + color: var(--heading-color) !important; + font-size: 1.25rem; + } + + %muted { + color: var(--text-muted-color) !important; + } + + .card-text.content { + @extend %muted; + + p { + @extend %text-clip; + + line-height: 1.5; + margin: 0; + } + } + + .post-meta { + @extend %muted; + + i { + &:not(:first-child) { + margin-left: 1.5rem; + } + } + + em { + @extend %normal-font-style; + + color: inherit; + } + + > div:first-child { + display: block; + white-space: nowrap; + overflow: hidden; + text-overflow: ellipsis; + } + } + } + } +} /* #post-list */ + +.pagination { + color: var(--text-color); + font-family: Lato, sans-serif; + justify-content: space-evenly; + + a:hover { + text-decoration: none; + } + + .page-item { + .page-link { + color: var(--btn-patinator-text-color); + padding: 0 0.6rem; + display: -webkit-box; + -webkit-box-pack: center; + -webkit-box-align: center; + border-radius: 0.5rem; + border: 0; + background-color: inherit; + } + + &.active { + .page-link { + background-color: var(--btn-paginator-hover-color); + } + } + + &:not(.active) { + .page-link { + &:hover { + box-shadow: inset var(--btn-border-color) 0 0 0 1px; + } + } + } + + &.disabled { + cursor: not-allowed; + + .page-link { + color: rgba(108, 117, 125, 0.57); + } + } + } /* .page-item */ +} /* .pagination */ + +/* Tablet */ +@media all and (min-width: 768px) { + %img-radius { + border-radius: 0 $base-radius $base-radius 0; + } + + #post-list { + .card { + .card-body { + padding: 1.75rem 1.75rem 1.25rem 1.75rem; + + .card-text { + display: inherit !important; + } + + .post-meta { + i { + &:not(:first-child) { + margin-left: 1.75rem; + } + } + } + } + } + } +} + +/* Hide SideBar and TOC */ +@media all and (max-width: 830px) { + .pagination { + .page-item { + &:not(:first-child):not(:last-child) { + display: none; + } + } + } +} + +/* Sidebar is visible */ +@media all and (min-width: 831px) { + #post-list { + margin-top: 2.5rem; + } + + .pagination { + font-size: 0.85rem; + justify-content: center; + + .page-item { + &:not(:last-child) { + margin-right: 0.7rem; + } + } + + .page-index { + display: none; + } + } /* .pagination */ +} diff --git a/_sass/layout/post.scss b/_sass/layout/post.scss new file mode 100644 index 0000000..112541d --- /dev/null +++ b/_sass/layout/post.scss @@ -0,0 +1,370 @@ +/* + Post-specific style +*/ + +%btn-post-nav { + width: 50%; + position: relative; + border-color: var(--btn-border-color); +} + +@mixin dot($pl: 0.25rem, $pr: 0.25rem) { + content: '\2022'; + padding-left: $pl; + padding-right: $pr; +} + +header { + .post-desc { + @extend %heading; + + font-size: 1.125rem; + line-height: 1.6; + } + + .post-meta { + span + span::before { + @include dot; + } + + em, + time { + @extend %text-highlight; + } + + em { + a { + color: inherit; + } + } + } + + h1 + .post-meta { + margin-top: 1.5rem; + } +} + +.post-tail-wrapper { + @extend %text-sm; + + margin-top: 6rem; + border-bottom: 1px double var(--main-border-color); + + .license-wrapper { + line-height: 1.2rem; + + > a { + @extend %text-highlight; + + &:hover { + @extend %link-hover; + } + } + + span:last-child { + @extend %text-sm; + } + } /* .license-wrapper */ + + .post-meta a:not(:hover) { + @extend %link-underline; + } + + .share-wrapper { + vertical-align: middle; + -webkit-user-select: none; + -moz-user-select: none; + -ms-user-select: none; + user-select: none; + + %icon-size { + font-size: 1.125rem; + } + + .share-icons { + display: flex; + + i { + color: var(--btn-share-color); + + @extend %icon-size; + } + + > * { + @extend %icon-size; + + margin-left: 0.5rem; + + &:hover { + i { + @extend %btn-share-hovor; + } + } + } + + button { + padding: 0; + border: none; + line-height: inherit; + + @extend %cursor-pointer; + } + } /* .share-icons */ + } /* .share-wrapper */ +} + +.share-mastodon { + /* See: https://github.com/justinribeiro/share-to-mastodon#properties */ + --wc-stm-font-family: $font-family-base; + --wc-stm-dialog-background-color: var(--card-bg); + --wc-stm-form-button-border: 1px solid var(--btn-border-color); + --wc-stm-form-submit-background-color: var(--sidebar-btn-bg); + --wc-stm-form-cancel-background-color: var(--sidebar-btn-bg); + --wc-stm-form-button-background-color-hover: #007bff; + --wc-stm-form-button-color-hover: white; + + font-size: 1rem; +} + +.post-tags { + line-height: 2rem; + + .post-tag { + &:hover { + @extend %link-hover; + @extend %tag-hover; + @extend %no-bottom-border; + } + } +} + +.post-navigation { + .btn { + @extend %btn-post-nav; + + &:not(:hover) { + color: var(--link-color); + } + + &:hover { + &:not(.disabled)::before { + color: whitesmoke; + } + } + + &.disabled { + @extend %btn-post-nav; + + pointer-events: auto; + cursor: not-allowed; + background: none; + color: gray; + } + + &.btn-outline-primary.disabled:focus { + box-shadow: none; + } + + &::before { + color: var(--text-muted-color); + font-size: 0.65rem; + text-transform: uppercase; + content: attr(aria-label); + } + + &:first-child { + border-radius: $base-radius 0 0 $base-radius; + left: 0.5px; + } + + &:last-child { + border-radius: 0 $base-radius $base-radius 0; + right: 0.5px; + } + } + + p { + font-size: 1.1rem; + line-height: 1.5rem; + margin-top: 0.3rem; + white-space: normal; + } +} /* .post-navigation */ + +@media (hover: hover) { + .post-navigation { + .btn, + .btn::before { + transition: all 0.35s ease-in-out; + } + } +} + +@-webkit-keyframes fade-up { + from { + opacity: 0; + position: relative; + top: 2rem; + } + + to { + opacity: 1; + position: relative; + top: 0; + } +} + +@keyframes fade-up { + from { + opacity: 0; + position: relative; + top: 2rem; + } + + to { + opacity: 1; + position: relative; + top: 0; + } +} + +#toc-wrapper { + border-left: 1px solid rgba(158, 158, 158, 0.17); + position: -webkit-sticky; + position: sticky; + top: 4rem; + transition: top 0.2s ease-in-out; + -webkit-animation: fade-up 0.8s; + animation: fade-up 0.8s; + + ul { + list-style: none; + font-size: 0.85rem; + line-height: 1.25; + padding-left: 0; + + li { + &:not(:last-child) { + margin: 0.4rem 0; + } + + a { + padding: 0.2rem 0 0.2rem 1.25rem; + } + } + + /* Overwrite TOC plugin style */ + + .toc-link { + display: block; + white-space: nowrap; + overflow: hidden; + text-overflow: ellipsis; + + &:hover { + color: var(--toc-highlight); + text-decoration: none; + } + + &::before { + display: none; + } + } + + .is-active-link { + color: var(--toc-highlight) !important; + font-weight: 600; + + &::before { + display: inline-block; + width: 1px; + left: -1px; + height: 1.25rem; + background-color: var(--toc-highlight) !important; + } + } + + ul { + padding-left: 0.75rem; + } + } +} + +/* --- Related Posts --- */ + +#related-posts { + > h3 { + @include label(1.1rem, 600); + } + + time { + @extend %normal-font-style; + @extend %text-xs; + + color: var(--text-muted-color); + } + + p { + font-size: 0.9rem; + margin-bottom: 0.5rem; + overflow: hidden; + text-overflow: ellipsis; + display: -webkit-box; + -webkit-line-clamp: 2; + -webkit-box-orient: vertical; + } + + .card { + h4 { + @extend %text-clip; + } + } +} + +/* stylelint-disable-next-line selector-id-pattern */ +#disqus_thread { + min-height: 8.5rem; +} + +.utterances { + max-width: 100%; +} + +%btn-share-hovor { + color: var(--btn-share-hover-color) !important; +} + +.share-label { + @include label(inherit, 400, inherit); + + &::after { + content: ':'; + } +} + +@media all and (max-width: 576px) { + .post-tail-bottom { + flex-wrap: wrap-reverse !important; + + > div:first-child { + width: 100%; + margin-top: 1rem; + } + } +} + +@media all and (max-width: 768px) { + .content > p > img { + max-width: calc(100% + 1rem); + } +} + +/* Hide SideBar and TOC */ +@media all and (max-width: 849px) { + .post-navigation { + padding-left: 0; + padding-right: 0; + margin-left: -0.5rem; + margin-right: -0.5rem; + } +} diff --git a/_sass/layout/tags.scss b/_sass/layout/tags.scss new file mode 100644 index 0000000..4cf5d3b --- /dev/null +++ b/_sass/layout/tags.scss @@ -0,0 +1,19 @@ +/* + Styles for Tab Tags +*/ + +.tag { + border-radius: 0.7em; + padding: 6px 8px 7px; + margin-right: 0.8rem; + line-height: 3rem; + letter-spacing: 0; + border: 1px solid var(--tag-border) !important; + box-shadow: 0 0 3px 0 var(--tag-shadow); + + span { + margin-left: 0.6em; + font-size: 0.7em; + font-family: Oswald, sans-serif; + } +} diff --git a/_sass/main.bundle.scss b/_sass/main.bundle.scss new file mode 100644 index 0000000..52e893f --- /dev/null +++ b/_sass/main.bundle.scss @@ -0,0 +1,2 @@ +@import 'dist/bootstrap'; +@import 'main'; diff --git a/_sass/main.scss b/_sass/main.scss new file mode 100644 index 0000000..1c2311d --- /dev/null +++ b/_sass/main.scss @@ -0,0 +1,13 @@ +@import 'colors/typography-light'; +@import 'colors/typography-dark'; +@import 'addon/variables'; +@import 'variables-hook'; +@import 'addon/module'; +@import 'addon/syntax'; +@import 'addon/commons'; +@import 'layout/home'; +@import 'layout/post'; +@import 'layout/tags'; +@import 'layout/archives'; +@import 'layout/categories'; +@import 'layout/category-tag'; diff --git a/_sass/variables-hook.scss b/_sass/variables-hook.scss new file mode 100644 index 0000000..f27e0eb --- /dev/null +++ b/_sass/variables-hook.scss @@ -0,0 +1,3 @@ +/* + Appending custom SCSS variables will override the default ones in `_sass/addon/variables.scsss` +*/ diff --git a/assets/404.html b/assets/404.html new file mode 100644 index 0000000..5b46cc8 --- /dev/null +++ b/assets/404.html @@ -0,0 +1,14 @@ +--- +layout: page +title: "404: Page not found" +permalink: /404.html + +redirect_from: + - /norobots/ + - /assets/ + - /posts/ +--- + +{% include lang.html %} + +

{{ site.data.locales[lang].not_found.statment }}

diff --git a/assets/css/jekyll-theme-chirpy.scss b/assets/css/jekyll-theme-chirpy.scss new file mode 100644 index 0000000..d20545b --- /dev/null +++ b/assets/css/jekyll-theme-chirpy.scss @@ -0,0 +1,10 @@ +--- +--- + +@import 'main +{%- if jekyll.environment == 'production' -%} + .bundle +{%- endif -%} +'; + +/* append your custom style below */ diff --git a/assets/feed.xml b/assets/feed.xml new file mode 100644 index 0000000..a244a56 --- /dev/null +++ b/assets/feed.xml @@ -0,0 +1,61 @@ +--- +layout: compress +permalink: /feed.xml +# Atom Feed, reference: https://validator.w3.org/feed/docs/atom.html +--- + +{% capture source %} + + {{ "/" | absolute_url }} + {{ site.title }} + {{ site.description }} + {{ site.time | date_to_xmlschema }} + + {{ site.social.name }} + {{ "/" | absolute_url }} + + + + Jekyll + © {{ 'now' | date: '%Y' }} {{ site.social.name }} + {{ site.baseurl }}/assets/img/favicons/favicon.ico + {{ site.baseurl }}/assets/img/favicons/favicon-96x96.png + +{% for post in site.posts limit: 5 %} + {% assign post_absolute_url = post.url | absolute_url %} + + {{ post.title }} + + {{ post.date | date_to_xmlschema }} + {% if post.last_modified_at %} + {{ post.last_modified_at | date_to_xmlschema }} + {% else %} + {{ post.date | date_to_xmlschema }} + {% endif %} + {{ post_absolute_url }} + + + {{ post.author | default: site.social.name }} + + + {% if post.categories %} + {% for category in post.categories %} + + {% endfor %} + {% endif %} + + {% if post.summary %} + {{ post.summary | strip }} + {% else %} + + {% include no-linenos.html content=post.content %} + {{ content | strip_html | truncate: 400 }} + + {% endif %} + + +{% endfor %} + +{% endcapture %} +{{ source | replace: '&', '&' }} diff --git a/assets/js/data/mathjax.js b/assets/js/data/mathjax.js new file mode 100644 index 0000000..ca3d0de --- /dev/null +++ b/assets/js/data/mathjax.js @@ -0,0 +1,25 @@ +--- +layout: compress +# WARNING: Don't use '//' to comment out code, use '{% comment %}' and '{% endcomment %}' instead. +--- + +{%- comment -%} + See: +{%- endcomment -%} + +MathJax = { + tex: { + {%- comment -%} start/end delimiter pairs for in-line math {%- endcomment -%} + inlineMath: [ + ['$', '$'], + ['\\(', '\\)'] + ], + {%- comment -%} start/end delimiter pairs for display math {%- endcomment -%} + displayMath: [ + ['$$', '$$'], + ['\\[', '\\]'] + ], + {%- comment -%} equation numbering {%- endcomment -%} + tags: 'ams' + } +}; diff --git a/assets/js/data/search.json b/assets/js/data/search.json new file mode 100644 index 0000000..2601ed0 --- /dev/null +++ b/assets/js/data/search.json @@ -0,0 +1,20 @@ +--- +layout: compress +swcache: true +--- + +[ + {% for post in site.posts %} + { + "title": {{ post.title | jsonify }}, + "url": {{ post.url | relative_url | jsonify }}, + "categories": {{ post.categories | join: ', ' | jsonify }}, + "tags": {{ post.tags | join: ', ' | jsonify }}, + "date": "{{ post.date }}", + {% include no-linenos.html content=post.content %} + {% assign _content = content | strip_html | strip_newlines %} + "snippet": {{ _content | truncate: 200 | jsonify }}, + "content": {{ _content | jsonify }} + }{% unless forloop.last %},{% endunless %} + {% endfor %} +] diff --git a/assets/js/data/swconf.js b/assets/js/data/swconf.js new file mode 100644 index 0000000..798888a --- /dev/null +++ b/assets/js/data/swconf.js @@ -0,0 +1,47 @@ +--- +layout: compress +permalink: '/:path/swconf.js' +# Note that this file will be fetched by the ServiceWorker, so it will not be cached. +--- + +const swconf = { + {% if site.pwa.cache.enabled %} + cacheName: 'chirpy-{{ "now" | date: "%s" }}', + + {%- comment -%} Resources added to the cache during PWA installation. {%- endcomment -%} + resources: [ + '{{ "/assets/css/:THEME.css" | replace: ':THEME', site.theme | relative_url }}', + '{{ "/" | relative_url }}', + {% for tab in site.tabs %} + '{{- tab.url | relative_url -}}', + {% endfor %} + + {% assign cache_list = site.static_files | where: 'swcache', true %} + {% for file in cache_list %} + '{{ file.path | relative_url }}'{%- unless forloop.last -%},{%- endunless -%} + {% endfor %} + ], + + interceptor: { + {%- comment -%} URLs containing the following paths will not be cached. {%- endcomment -%} + paths: [ + {% for path in site.pwa.cache.deny_paths %} + {% unless path == empty %} + '{{ path | relative_url }}'{%- unless forloop.last -%},{%- endunless -%} + {% endunless %} + {% endfor %} + ], + + {%- comment -%} URLs containing the following prefixes will not be cached. {%- endcomment -%} + urlPrefixes: [ + {% if site.analytics.goatcounter.id != nil and site.pageviews.provider == 'goatcounter' %} + 'https://{{ site.analytics.goatcounter.id }}.goatcounter.com/counter/' + {% endif %} + ] + }, + + purge: false + {% else %} + purge: true + {% endif %} +}; diff --git a/assets/robots.txt b/assets/robots.txt new file mode 100644 index 0000000..45c34e0 --- /dev/null +++ b/assets/robots.txt @@ -0,0 +1,10 @@ +--- +permalink: /robots.txt +# The robots rules +--- + +User-agent: * + +Disallow: /norobots/ + +Sitemap: {{ '/sitemap.xml' | absolute_url }}