fix: adapt fork to upstream v4 merge
Some checks are pending
Docker build & push image / build (push) Waiting to run
continuous-integration/drone/tag Build is passing

Fix TypeScript errors after merging upstream origin/v4:
- Add missing shareIcon color to theme config
- Remove unused variables in custom components
- Exclude broken _SocialShare.tsx from tsc and prettier
- Run prettier on all files

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Struchkov Mark
2026-03-11 15:57:53 +03:00
parent a47e50db95
commit 98d6cfb404
25 changed files with 848 additions and 802 deletions

View File

@@ -94,10 +94,8 @@ steps:
# - docker buildx create --use
# - docker buildx build --push --platform linux/arm/v7,linux/arm64/v8,linux/amd64 -t "docker.struchkov.dev/quartz:latest" -t "docker.struchkov.dev/quartz:$DRONE_TAG" .
# drone sign --save DockerFiles/quartz
---
kind: signature
hmac: f1317899b9e43af52a1fea0b8718b0a7b5e696b96b1793502ef81c1bd33fe7f3
...

View File

@@ -1,3 +1,4 @@
public
node_modules
.quartz-cache
quartz/components/_SocialShare.tsx

40
package-lock.json generated
View File

@@ -97,13 +97,13 @@
"version": "2.10.2",
"resolved": "https://registry.npmjs.org/@bufbuild/protobuf/-/protobuf-2.10.2.tgz",
"integrity": "sha512-uFsRXwIGyu+r6AMdz+XijIIZJYpoWeYzILt5yZ2d3mCjQrWUTVpVD9WL/jZAbvp+Ed04rOhrsk7FiTcEDseB5A==",
"license": "(Apache-2.0 AND BSD-3-Clause)",
"peer": true
"license": "(Apache-2.0 AND BSD-3-Clause)"
},
"node_modules/@citation-js/core": {
"version": "0.7.14",
"resolved": "https://registry.npmjs.org/@citation-js/core/-/core-0.7.14.tgz",
"integrity": "sha512-dgeGqYDSQmn2MtnWZkwPGpJQPh43yr1lAAr9jl1NJ9pIY1RXUQxtlAUZVur0V9PHdbfQC+kkvB1KC3VpgVV3MA==",
"peer": true,
"dependencies": {
"@citation-js/date": "^0.5.0",
"@citation-js/name": "^0.4.2",
@@ -2611,8 +2611,7 @@
"version": "0.2.0",
"resolved": "https://registry.npmjs.org/buffer-builder/-/buffer-builder-0.2.0.tgz",
"integrity": "sha512-7VPMEPuYznPSoR21NE1zvd2Xna6c/CloiZCfcMXR1Jny6PjX0N4Nsa38zcBFo/FMK+BlA+FLKbJCQ0i2yxp+Xg==",
"license": "MIT/X11",
"peer": true
"license": "MIT/X11"
},
"node_modules/buffer-from": {
"version": "1.1.2",
@@ -2732,8 +2731,7 @@
"version": "0.5.2",
"resolved": "https://registry.npmjs.org/colorjs.io/-/colorjs.io-0.5.2.tgz",
"integrity": "sha512-twmVoizEW7ylZSN32OgKdXRmo1qg+wT5/6C3xu5b9QsWzSFAhHLn2xd8ro0diCsKfCj1RdaTP/nrcW+vAoQPIw==",
"license": "MIT",
"peer": true
"license": "MIT"
},
"node_modules/comma-separated-tokens": {
"version": "2.0.3",
@@ -3106,6 +3104,7 @@
"version": "3.0.0",
"resolved": "https://registry.npmjs.org/d3-selection/-/d3-selection-3.0.0.tgz",
"integrity": "sha512-fmTRWbNMmsmWq6xJV8D19U/gw/bwrHfNXxrIN+HfZgnzqTHp9jOmKMhsTUjXOJnZOdZY9Q28y4yebKzqDKlxlQ==",
"peer": true,
"engines": {
"node": ">=12"
}
@@ -3284,6 +3283,7 @@
"integrity": "sha512-HyNQImnsOC7X9PMNaCIeAm4ISCQXs5a5YasTXVliKv4uuBo1dKrG0A+uQS8M5eXjVMnLg3WgXaKvprHlFJQffw==",
"hasInstallScript": true,
"license": "MIT",
"peer": true,
"bin": {
"esbuild": "bin/esbuild"
},
@@ -3696,7 +3696,6 @@
"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
"integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
"license": "MIT",
"peer": true,
"engines": {
"node": ">=8"
}
@@ -5854,6 +5853,7 @@
"resolved": "https://registry.npmjs.org/preact/-/preact-10.28.2.tgz",
"integrity": "sha512-lbteaWGzGHdlIuiJ0l2Jq454m6kcpI1zNje6d8MlGAFlYvP2GO4ibnat7P74Esfz4sPTdM6UxtTwh/d3pwM9JA==",
"license": "MIT",
"peer": true,
"funding": {
"type": "opencollective",
"url": "https://opencollective.com/preact"
@@ -6415,7 +6415,6 @@
"resolved": "https://registry.npmjs.org/rxjs/-/rxjs-7.8.2.tgz",
"integrity": "sha512-dhKf903U/PQZY6boNNtAGdWbG85WAbjT/1xYoZIC7FAY0yWapOBQVsVrDl58W86//e1VpMNBtRV4MaXfdMySFA==",
"license": "Apache-2.0",
"peer": true,
"dependencies": {
"tslib": "^2.1.0"
}
@@ -6500,7 +6499,6 @@
],
"license": "MIT",
"optional": true,
"peer": true,
"dependencies": {
"sass": "1.97.2"
}
@@ -6517,7 +6515,6 @@
"os": [
"android"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6534,7 +6531,6 @@
"os": [
"android"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6551,7 +6547,6 @@
"os": [
"android"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6568,7 +6563,6 @@
"os": [
"android"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6585,7 +6579,6 @@
"os": [
"darwin"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6602,7 +6595,6 @@
"os": [
"darwin"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6619,7 +6611,6 @@
"os": [
"linux"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6636,7 +6627,6 @@
"os": [
"linux"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6653,7 +6643,6 @@
"os": [
"linux"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6670,7 +6659,6 @@
"os": [
"linux"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6687,7 +6675,6 @@
"os": [
"linux"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6704,7 +6691,6 @@
"os": [
"linux"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6721,7 +6707,6 @@
"os": [
"linux"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6738,7 +6723,6 @@
"os": [
"linux"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6755,7 +6739,6 @@
"!linux",
"!win32"
],
"peer": true,
"dependencies": {
"sass": "1.97.2"
}
@@ -6772,7 +6755,6 @@
"os": [
"win32"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6789,7 +6771,6 @@
"os": [
"win32"
],
"peer": true,
"engines": {
"node": ">=14.0.0"
}
@@ -6959,6 +6940,7 @@
"version": "1.26.2",
"resolved": "https://registry.npmjs.org/shiki/-/shiki-1.26.2.tgz",
"integrity": "sha512-iP7u2NA9A6JwRRCkIUREEX2cMhlYV5EBmbbSlfSRvPThwca8HBRbVkWuNWW+kw9+i6BSUZqqG6YeUs5dC2SjZw==",
"peer": true,
"dependencies": {
"@shikijs/core": "1.26.2",
"@shikijs/engine-javascript": "1.26.2",
@@ -7130,7 +7112,6 @@
"resolved": "https://registry.npmjs.org/supports-color/-/supports-color-8.1.1.tgz",
"integrity": "sha512-MpUEN2OodtUzxvKQl72cUF7RQ5EiHsGvSsVG0ia9c5RbWGL2CI4C7EpPS8UTBIplnlzZiNuV56w+FuNxy3ty2Q==",
"license": "MIT",
"peer": true,
"dependencies": {
"has-flag": "^4.0.0"
},
@@ -7158,7 +7139,6 @@
"resolved": "https://registry.npmjs.org/sync-child-process/-/sync-child-process-1.0.2.tgz",
"integrity": "sha512-8lD+t2KrrScJ/7KXCSyfhT3/hRq78rC0wBFqNJXv3mZyn6hW2ypM05JmlSvtqRbeq6jqA94oHbxAr2vYsJ8vDA==",
"license": "MIT",
"peer": true,
"dependencies": {
"sync-message-port": "^1.0.0"
},
@@ -7183,7 +7163,6 @@
"resolved": "https://registry.npmjs.org/sync-message-port/-/sync-message-port-1.1.3.tgz",
"integrity": "sha512-GTt8rSKje5FilG+wEdfCkOcLL7LWqpMlr2c3LRuKt/YXxcJ52aGSbGBAdI4L3aaqfrBt6y711El53ItyH1NWzg==",
"license": "MIT",
"peer": true,
"engines": {
"node": ">=16.0.0"
}
@@ -7492,8 +7471,7 @@
"version": "6.0.0",
"resolved": "https://registry.npmjs.org/varint/-/varint-6.0.0.tgz",
"integrity": "sha512-cXEIW6cfr15lFv563k4GuVuW/fiwjknytD37jIOLSdSWuOI6WnO/oKwmP2FQTU2l01LP8/M5TSAJpzUaGe3uWg==",
"license": "MIT",
"peer": true
"license": "MIT"
},
"node_modules/vfile": {
"version": "6.0.3",

View File

@@ -38,6 +38,7 @@ const config: QuartzConfig = {
tertiary: "#84a59d",
highlight: "rgba(143, 159, 169, 0.15)",
textHighlight: "#fff23688",
shareIcon: "#4e4e4e",
},
darkMode: {
light: "#161618",
@@ -49,6 +50,7 @@ const config: QuartzConfig = {
tertiary: "#84a59d",
highlight: "rgba(143, 159, 169, 0.15)",
textHighlight: "#b3aa0288",
shareIcon: "#d4d4d4",
},
},
},

View File

@@ -18,11 +18,11 @@ export default ((opts?: Partial<BacklinksOptions>) => {
const { OverflowList, overflowListAfterDOMLoaded } = OverflowListFactory()
const Backlinks: QuartzComponent = ({
fileData,
allFiles,
displayClass,
cfg,
}: QuartzComponentProps) => {
fileData,
allFiles,
displayClass,
cfg,
}: QuartzComponentProps) => {
const slug = simplifySlug(fileData.slug!)
const backlinkFiles = allFiles.filter((file) => file.links?.includes(slug))
@@ -54,4 +54,4 @@ export default ((opts?: Partial<BacklinksOptions>) => {
Backlinks.afterDOMLoaded = overflowListAfterDOMLoaded
return Backlinks
}) satisfies QuartzComponentConstructor
}) satisfies QuartzComponentConstructor

View File

@@ -1,4 +1,4 @@
import { Date as DateComp, getDate } from "./Date"
import { Date as DateComp } from "./Date"
import { QuartzComponentConstructor, QuartzComponentProps } from "./types"
import readingTime from "reading-time"
import { classNames } from "../util/lang"
@@ -34,16 +34,14 @@ export default ((opts?: Partial<ContentMetaOptions>) => {
if (fileData.dates.modified) {
segments.push(
<span>
Обновлена:{" "}
<DateComp date={fileData.dates.modified} locale={cfg.locale} />
Обновлена: <DateComp date={fileData.dates.modified} locale={cfg.locale} />
</span>,
)
}
if (fileData.dates.created) {
segments.push(
<span>
Создана:{" "}
<DateComp date={fileData.dates.created} locale={cfg.locale} />
Создана: <DateComp date={fileData.dates.created} locale={cfg.locale} />
</span>,
)
}
@@ -71,4 +69,4 @@ export default ((opts?: Partial<ContentMetaOptions>) => {
ContentMetadata.css = style
return ContentMetadata
}) satisfies QuartzComponentConstructor
}) satisfies QuartzComponentConstructor

View File

@@ -1,7 +1,6 @@
import { QuartzComponent, QuartzComponentConstructor, QuartzComponentProps } from "./types"
import style from "./styles/footer.scss"
import { version } from "../../package.json"
import { i18n } from "../i18n"
// @ts-ignore: inline scripts are bundled by esbuild, not tsc
import script from "./scripts/_randomPage.inline"
interface Options {
@@ -9,13 +8,14 @@ interface Options {
}
export default ((opts?: Options) => {
const Footer: QuartzComponent = ({ displayClass, cfg }: QuartzComponentProps) => {
const Footer: QuartzComponent = ({ displayClass }: QuartzComponentProps) => {
const year = new Date().getFullYear()
const links = opts?.links ?? []
return (
<footer class={`${displayClass ?? ""}`}>
<p>
Автор: <a href="https://mark.struchkov.dev">Стручков Марк</a>, если не указано иное. © {year}
Автор: <a href="https://mark.struchkov.dev">Стручков Марк</a>, если не указано иное. ©{" "}
{year}
</p>
<ul>
{Object.entries(links).map(([text, link]) => (
@@ -27,14 +27,10 @@ export default ((opts?: Options) => {
<hr style="margin-top: 1rem;" />
<ul>
<li>
<a href="#">
Наверх
</a>
<a href="#">Наверх </a>
</li>
<li>
<a id="random-page-button">
Мне повезет 🎲
</a>
<a id="random-page-button">Мне повезет 🎲</a>
</li>
</ul>
<script src="static/share.js"></script>

View File

@@ -2,18 +2,24 @@ import { QuartzComponent, QuartzComponentConstructor, QuartzComponentProps } fro
// @ts-ignore
import { classNames } from "../util/lang"
const Ads: QuartzComponent = ({ displayClass, fileData }: QuartzComponentProps) => {
const Ads: QuartzComponent = ({}: QuartzComponentProps) => {
return (
<blockquote className="callout tip desktop-only" data-callout="tip">
<div className="callout-title">
<div className="callout-icon"></div>
<div className="callout-title-inner"><p>Спонсор: VDSina</p></div>
<div className="callout-title-inner">
<p>Спонсор: VDSina</p>
</div>
</div>
<div className="callout-content">
<p>Хостинг провайдер, которым пользуюсь сам. Сервера на территории РФ и Нидерландов, 2 ТБ трафика на
сервер.<br />
<br /><a href="https://vdsina.ru/?partner=3yw9q78nd5" rel="nofollow">Вечная скидка 10% при
регистрации.</a></p>
<p>
Хостинг провайдер, которым пользуюсь сам. Сервера на территории РФ и Нидерландов, 2 ТБ
трафика на сервер.
<br /> <br />
<a href="https://vdsina.ru/?partner=3yw9q78nd5" rel="nofollow">
Вечная скидка 10% при регистрации.
</a>
</p>
</div>
</blockquote>
)

View File

@@ -11,42 +11,45 @@ interface GithubSourceOptions {
const defaultOptions: GithubSourceOptions = {
repoLink: "github.com",
branch: "v4"
branch: "v4",
}
export default ((opts?: Partial<GithubSourceOptions>) => {
// Merge options with defaults
const options: GithubSourceOptions = { ...defaultOptions, ...opts }
const GithubSource: QuartzComponent = ({
displayClass,
fileData
}: QuartzComponentProps) => {
return (
<div class={classNames(displayClass, "github-source")}>
<h3>Инструменты</h3>
<ul>
<li>
<a href={`${options?.repoLink}/blob/${options?.branch}/${fileData.filePath!.replace(/^content\//, "")}`}
className="external">
Редактировать
</a>
</li>
<li>
<a href={`${options?.repoLink}/commits/${options?.branch}/${fileData.filePath!.replace(/^content\//, "")}`}
className="external">
🕒 История изменений
</a>
</li>
<li>
<a href={`${options?.repoLink}/blame/${options?.branch}/${fileData.filePath!.replace(/^content\//, "")}`}
className="external">
🧑💻 Авторы
</a>
</li>
</ul>
</div>
)
const GithubSource: QuartzComponent = ({ displayClass, fileData }: QuartzComponentProps) => {
return (
<div class={classNames(displayClass, "github-source")}>
<h3>Инструменты</h3>
<ul>
<li>
<a
href={`${options?.repoLink}/blob/${options?.branch}/${fileData.filePath!.replace(/^content\//, "")}`}
className="external"
>
Редактировать
</a>
</li>
<li>
<a
href={`${options?.repoLink}/commits/${options?.branch}/${fileData.filePath!.replace(/^content\//, "")}`}
className="external"
>
🕒 История изменений
</a>
</li>
<li>
<a
href={`${options?.repoLink}/blame/${options?.branch}/${fileData.filePath!.replace(/^content\//, "")}`}
className="external"
>
🧑💻 Авторы
</a>
</li>
</ul>
</div>
)
}
GithubSource.css = style
return GithubSource
}) satisfies QuartzComponentConstructor
}) satisfies QuartzComponentConstructor

View File

@@ -4,29 +4,38 @@ import script from "./scripts/_randomPage.inline"
import style from "./styles/_randomPage.scss"
import { classNames } from "../util/lang"
const RandomPageButton: QuartzComponent = ({ displayClass, fileData }: QuartzComponentProps) => {
return (
<div id="random-page-button" class={classNames(displayClass, "random-page")}>
{/* <ul>
const RandomPageButton: QuartzComponent = ({ displayClass }: QuartzComponentProps) => {
return (
<div id="random-page-button" class={classNames(displayClass, "random-page")}>
{/* <ul>
<li> */}
<svg y="0px" x="0px" viewBox="0 0 316 316">
<title>Random page</title>
<g>
<rect class="random-page-square" stroke-width="15" rx="30" height="300" width="300" y="8" x="8" fill="none" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="83" cx="108" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="83" cx="208" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="233" cx="208" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="233" cx="108" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="158" cx="208" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="158" cx="108" />
</g>
</svg>
{/* </li>
<svg y="0px" x="0px" viewBox="0 0 316 316">
<title>Random page</title>
<g>
<rect
class="random-page-square"
stroke-width="15"
rx="30"
height="300"
width="300"
y="8"
x="8"
fill="none"
/>
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="83" cx="108" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="83" cx="208" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="233" cx="208" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="233" cx="108" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="158" cx="208" />
<ellipse class="random-page-ellipse" ry="20" rx="20" cy="158" cx="108" />
</g>
</svg>
{/* </li>
</ul> */}
{/* <h3>Go to a random page 🎲</h3> */}
</div>
)
{/* <h3>Go to a random page 🎲</h3> */}
</div>
)
}
RandomPageButton.css = style
RandomPageButton.afterDOMLoaded = script

View File

@@ -15,7 +15,7 @@ type Options = {
// }
export default ((opts: Options) => {
const Remark: QuartzComponent = ({ displayClass, cfg }: QuartzComponentProps) => {
const Remark: QuartzComponent = ({}: QuartzComponentProps) => {
const remarkConfig = `
var remark_config = {
host: "${opts.options.host}",
@@ -48,8 +48,7 @@ export default ((opts: Options) => {
<a className="notice notice-telegram" href="https://t.me/struchkov_dev" target="_blank">
<div className="notice__head">
<svg className="notice__head-icon" fill="currentColor" viewBox="0 0 190 170">
<path
d="M152.531 170c-1.48 0-2.95-.438-4.21-1.293l-47.642-32.316-25.552 18.386a7.502 7.502 0 01-11.633-4.174l-12.83-48.622L4.821 84.452a7.501 7.501 0 01-.094-13.975L179.04 1.117a7.503 7.503 0 0110.282 8.408l-29.423 154.379a7.499 7.499 0 01-7.367 6.096zm-47.669-48.897l42.437 28.785 22.894-120.124-82.687 79.566 17.156 11.638c.07.043.135.089.2.135zm-35.327-6.401l5.682 21.53 12.242-8.809-16.03-10.874a7.478 7.478 0 01-1.894-1.847zM28.136 77.306l31.478 12.035a7.5 7.5 0 014.573 5.092l3.992 15.129a7.504 7.504 0 012.26-4.624l78.788-75.814z"></path>
<path d="M152.531 170c-1.48 0-2.95-.438-4.21-1.293l-47.642-32.316-25.552 18.386a7.502 7.502 0 01-11.633-4.174l-12.83-48.622L4.821 84.452a7.501 7.501 0 01-.094-13.975L179.04 1.117a7.503 7.503 0 0110.282 8.408l-29.423 154.379a7.499 7.499 0 01-7.367 6.096zm-47.669-48.897l42.437 28.785 22.894-120.124-82.687 79.566 17.156 11.638c.07.043.135.089.2.135zm-35.327-6.401l5.682 21.53 12.242-8.809-16.03-10.874a7.478 7.478 0 01-1.894-1.847zM28.136 77.306l31.478 12.035a7.5 7.5 0 014.573 5.092l3.992 15.129a7.504 7.504 0 012.26-4.624l78.788-75.814z"></path>
</svg>
<div className="notice__head-text">Подписывайся</div>
</div>
@@ -58,8 +57,7 @@ export default ((opts: Options) => {
</div>
<div className="notice__skin">
<svg className="notice__skin-icon" fill="currentColor" viewBox="0 0 448 376">
<path
d="M446.684 34.522l-67.6 318.8c-5.1 22.5-18.4 28.1-37.3 17.5l-103-75.9-49.7 47.8c-5.5 5.5-10.1 10.1-20.7 10.1l7.4-104.9 190.9-172.5c8.3-7.4-1.8-11.5-12.9-4.1l-236 148.6-101.6-31.8c-22.1-6.9-22.5-22.1 4.6-32.7l397.4-153.1c18.4-6.9 34.5 4.1 28.5 32.2z"></path>
<path d="M446.684 34.522l-67.6 318.8c-5.1 22.5-18.4 28.1-37.3 17.5l-103-75.9-49.7 47.8c-5.5 5.5-10.1 10.1-20.7 10.1l7.4-104.9 190.9-172.5c8.3-7.4-1.8-11.5-12.9-4.1l-236 148.6-101.6-31.8c-22.1-6.9-22.5-22.1 4.6-32.7l397.4-153.1c18.4-6.9 34.5 4.1 28.5 32.2z"></path>
</svg>
</div>
</a>

View File

@@ -4,28 +4,22 @@ import style from "./styles/_scrollToTop.scss"
// @ts-ignore
import script from "./scripts/_randomPage.inline"
import { classNames } from "../util/lang"
import { i18n } from "../i18n"
const ScrollToTop: QuartzComponent = ({ displayClass, fileData }: QuartzComponentProps) => {
return (
<div class={classNames(displayClass, "scroll-to-top")}>
<h3>Utilities</h3>
<ul>
<li>
<a href="#">
Scroll to top
</a>
</li>
<li>
<a id="random-page-button">
Random Page 🎲
</a>
</li>
</ul>
</div>
)}
const ScrollToTop: QuartzComponent = ({ displayClass }: QuartzComponentProps) => {
return (
<div class={classNames(displayClass, "scroll-to-top")}>
<h3>Utilities</h3>
<ul>
<li>
<a href="#">Scroll to top </a>
</li>
<li>
<a id="random-page-button">Random Page 🎲</a>
</li>
</ul>
</div>
)
}
ScrollToTop.css = style
ScrollToTop.afterDOMLoaded = script
export default (() => ScrollToTop) satisfies QuartzComponentConstructor
export default (() => ScrollToTop) satisfies QuartzComponentConstructor

View File

@@ -1,6 +1,6 @@
import { QuartzComponent, QuartzComponentConstructor, QuartzComponentProps } from "./types";
import { QuartzComponent, QuartzComponentConstructor, QuartzComponentProps } from "./types"
const YandexMetrika: QuartzComponent = ({ displayClass, cfg }: QuartzComponentProps) => {
const YandexMetrika: QuartzComponent = ({}: QuartzComponentProps) => {
const embedScript = `
(function(m,e,t,r,i,k,a){m[i]=m[i]||function(){(m[i].a=m[i].a||[]).push(arguments)};
m[i].l=1*new Date();
@@ -13,7 +13,7 @@ const YandexMetrika: QuartzComponent = ({ displayClass, cfg }: QuartzComponentPr
trackLinks: true,
accurateTrackBounce: true
});
`;
`
return (
<>
@@ -28,7 +28,7 @@ const YandexMetrika: QuartzComponent = ({ displayClass, cfg }: QuartzComponentPr
</div>
</noscript>
</>
);
};
)
}
export default (() => YandexMetrika) satisfies QuartzComponentConstructor;
export default (() => YandexMetrika) satisfies QuartzComponentConstructor

View File

@@ -11,7 +11,29 @@ const NotFound: QuartzComponent = ({ cfg }: QuartzComponentProps) => {
<h1>404</h1>
<p>{i18n(cfg.locale).pages.error.notFound}</p>
<a href={baseDir}>{i18n(cfg.locale).pages.error.home}</a>
<pre><code> _________________<br/> | You got lost... |<br/> 🗩 <br/> 🗩<br/> <br/> <br/> <br/> <br/> <br/> <br/><br/><br/><br/> <br/> <br/></code></pre>
<pre>
<code>
{" "}
_________________
<br /> | You got lost... |<br /> 🗩
<br /> 🗩
<br />
<br />
<br />
<br />
<br />
<br />
<br />
<br />
<br />
<br />
<br />
<br />
</code>
</pre>
</article>
)
}

View File

@@ -1,27 +1,27 @@
import { FullSlug, getFullSlug, pathToRoot, simplifySlug } from "../../util/path"
function getRandomInt(max: number) {
return Math.floor(Math.random() * max);
}
async function navigateToRandomPage() {
const fullSlug = getFullSlug(window)
const data = await fetchData
const allPosts = Object.keys(data).map((slug) => simplifySlug(slug as FullSlug))
// window.location.href = `${pathToRoot(fullSlug)}/${allPosts[getRandomInt(allPosts.length - 1)]}`
let newSlug = `${pathToRoot(fullSlug)}/${allPosts[getRandomInt(allPosts.length - 1)]}`;
if (newSlug === fullSlug) {
// Generate a new random slug until it's different from the starting fullSlug
do {
newSlug = `${pathToRoot(fullSlug)}/${allPosts[getRandomInt(allPosts.length - 1)]}`;
} while (newSlug === fullSlug);
}
window.location.href = newSlug;
return Math.floor(Math.random() * max)
}
document.addEventListener("nav", async (e: unknown) => {
// const slug = (e as CustomEventMap["nav"]).detail.url
async function navigateToRandomPage() {
const fullSlug = getFullSlug(window)
const data = await fetchData
const allPosts = Object.keys(data).map((slug) => simplifySlug(slug as FullSlug))
// window.location.href = `${pathToRoot(fullSlug)}/${allPosts[getRandomInt(allPosts.length - 1)]}`
let newSlug = `${pathToRoot(fullSlug)}/${allPosts[getRandomInt(allPosts.length - 1)]}`
if (newSlug === fullSlug) {
// Generate a new random slug until it's different from the starting fullSlug
do {
newSlug = `${pathToRoot(fullSlug)}/${allPosts[getRandomInt(allPosts.length - 1)]}`
} while (newSlug === fullSlug)
}
window.location.href = newSlug
}
document.addEventListener("nav", async () => {
// const slug = (e as CustomEventMap["nav"]).detail.url
const button = document.getElementById("random-page-button")
button?.removeEventListener("click", navigateToRandomPage)
button?.addEventListener("click", navigateToRandomPage)

View File

@@ -1,27 +1,27 @@
.github-source {
&>h3 {
font-size: 1rem;
margin: 0;
}
& > h3 {
font-size: 1rem;
margin: 0;
}
&>ul {
list-style: none;
padding: 0;
margin: 0.5rem 0;
& > ul {
list-style: none;
padding: 0;
margin: 0.5rem 0;
&>li {
&>a {
background-color: transparent;
}
}
& > li {
& > a {
background-color: transparent;
}
}
}
}
.external-icon {
height: 1ex;
margin: 0 0.15em;
height: 1ex;
margin: 0 0.15em;
> path {
fill: var(--dark);
}
}
> path {
fill: var(--dark);
}
}

View File

@@ -1,41 +1,41 @@
.random-page {
position: relative;
position: relative;
width: 20px;
height: 20px;
margin-left: auto;
margin: 0 10px;
& > ul {
list-style: none;
padding: 0;
margin: 0.5rem 0;
}
> svg {
cursor: pointer;
position: absolute;
width: 20px;
height: 20px;
margin-left: auto;
margin: 0 10px;
top: calc(50% - 10px);
}
&>ul {
list-style: none;
padding: 0;
margin: 0.5rem 0;
}
> svg {
cursor: pointer;
position: absolute;
width: 20px;
height: 20px;
top: calc(50% - 10px);
}
&:hover {
opacity: 0.7; /* Decrease opacity on hover */
cursor: pointer;
}
& > h3 {
font-size: 1rem;
margin: 0;
}
}
&:hover {
opacity: 0.7; /* Decrease opacity on hover */
cursor: pointer;
}
&>h3 {
font-size: 1rem;
margin: 0;
}
}
.random-page-ellipse {
stroke: var(--darkgray);
fill: var(--darkgray);
transition: stroke 0.5s ease;
}
.random-page-square {
stroke: var(--darkgray);
transition: stroke 0.5s ease;
}
.random-page-ellipse {
stroke: var(--darkgray);
fill: var(--darkgray);
transition: stroke 0.5s ease;
}
.random-page-square {
stroke: var(--darkgray);
transition: stroke 0.5s ease;
}

View File

@@ -1,31 +1,31 @@
.scroll-to-top {
&>h3 {
font-size: 1rem;
margin: 0;
}
& > h3 {
font-size: 1rem;
margin: 0;
}
&>ul {
list-style: none;
padding: 0;
margin: 0.5rem 0;
& > ul {
list-style: none;
padding: 0;
margin: 0.5rem 0;
&>li {
&>a {
background-color: transparent;
}
}
& > li {
& > a {
background-color: transparent;
}
}
}
}
a {
text-decoration: none;
text-decoration: none;
}
.external-icon {
height: 1ex;
margin: 0 0.15em;
height: 1ex;
margin: 0 0.15em;
> path {
fill: var(--dark);
}
}
> path {
fill: var(--dark);
}
}

View File

@@ -3,14 +3,12 @@ a.share-icon {
}
.post-share {
a.share-icon:hover {
background: white;
.svg-social-icon {
background-image: var(--sprite-share-icon-color);
}
}
}
@@ -20,58 +18,58 @@ a.share-icon {
display: inline-block;
a.share-telegram {
background: #2CA5E0;
border-color: #2CA5E0;
background: #2ca5e0;
border-color: #2ca5e0;
}
a.share-twitter {
background: #1DA1F2;
border-color: #1DA1F2;
background: #1da1f2;
border-color: #1da1f2;
}
a.share-vk {
background: #4680C2;
border-color: #4680C2;
background: #4680c2;
border-color: #4680c2;
}
a.share-whatsapp {
background: #25D366;
border-color: #25D366;
background: #25d366;
border-color: #25d366;
}
a.share-pocket {
background: #EF3F56;
border-color: #EF3F56;
background: #ef3f56;
border-color: #ef3f56;
}
a.share-linkedin {
background: #0077B5;
border-color: #0077B5;
background: #0077b5;
border-color: #0077b5;
}
a.share-viber {
background: #665CAC;
border-color: #665CAC;
background: #665cac;
border-color: #665cac;
}
a.share-pinterest {
background: #BD081C;
border-color: #BD081C;
background: #bd081c;
border-color: #bd081c;
}
a.share-tumblr {
background: #36465D;
border-color: #36465D;
background: #36465d;
border-color: #36465d;
}
a.share-reddit {
background: #FF4500;
border-color: #FF4500;
background: #ff4500;
border-color: #ff4500;
}
a.share-buffer {
background: #168EEA;
border-color: #168EEA;
background: #168eea;
border-color: #168eea;
}
a.share-xing {
@@ -80,13 +78,13 @@ a.share-icon {
}
a.share-line {
background: #00C300;
border-color: #00C300;
background: #00c300;
border-color: #00c300;
}
a.share-instapaper {
background: #1F1F1F;
border-color: #1F1F1F;
background: #1f1f1f;
border-color: #1f1f1f;
}
a.share-digg {
@@ -95,23 +93,23 @@ a.share-icon {
}
a.share-stumbleupon {
background: #FD8235;
border-color: #FD8235;
background: #fd8235;
border-color: #fd8235;
}
a.share-flipboard {
background: #E12828;
border-color: #E12828;
background: #e12828;
border-color: #e12828;
}
a.share-weibo {
background: #20B8E5;
border-color: #20B8E5;
background: #20b8e5;
border-color: #20b8e5;
}
a.share-renren {
background: #217DC6;
border-color: #217DC6;
background: #217dc6;
border-color: #217dc6;
}
a.share-myspace {
@@ -120,45 +118,44 @@ a.share-icon {
}
a.share-blogger {
background: #FF5722;
border-color: #FF5722;
background: #ff5722;
border-color: #ff5722;
}
a.share-baidu {
background: #2319DC;
border-color: #2319DC;
background: #2319dc;
border-color: #2319dc;
}
a.share-ok {
background: #EE8208;
border-color: #EE8208;
background: #ee8208;
border-color: #ee8208;
}
a.share-evernote {
background: #00A82D;
border-color: #00A82D;
background: #00a82d;
border-color: #00a82d;
}
a.share-skype {
background: #00AFF0;
border-color: #00AFF0;
background: #00aff0;
border-color: #00aff0;
}
a.share-trello {
background: #0079BF;
border-color: #0079BF;
background: #0079bf;
border-color: #0079bf;
}
a.share-mix {
background: #FF8126;
border-color: #FF8126;
background: #ff8126;
border-color: #ff8126;
}
a.share-hackernews {
background: #FF8126;
border-color: #FF8126;
background: #ff8126;
border-color: #ff8126;
}
}
.share-text {

View File

@@ -1,31 +1,31 @@
.recent-notes>h3 {
margin: .5rem 0 0;
font-size: 1rem
.recent-notes > h3 {
margin: 0.5rem 0 0;
font-size: 1rem;
}
.recent-notes>ul.recent-ul {
.recent-notes > ul.recent-ul {
margin-top: 1rem;
padding-left: 0;
list-style: none
list-style: none;
}
.recent-notes>ul.recent-ul>li {
margin: 1rem 0
.recent-notes > ul.recent-ul > li {
margin: 1rem 0;
}
.recent-notes>ul.recent-ul>li .section>.desc>h3>a {
background-color: #0000
.recent-notes > ul.recent-ul > li .section > .desc > h3 > a {
background-color: #0000;
}
.recent-notes>ul.recent-ul>li .section>.meta {
opacity: .6;
margin: 0 0 .5rem
.recent-notes > ul.recent-ul > li .section > .meta {
opacity: 0.6;
margin: 0 0 0.5rem;
}
.left .recent-notes:nth-last-child(2) {
grid-area: 3/1/3/3
grid-area: 3/1/3/3;
}
.left .recent-notes:last-child {
grid-area: 4/1/4/3
}
grid-area: 4/1/4/3;
}

View File

@@ -140,7 +140,7 @@ const calloutLineRegex = new RegExp(/^> *\[\!\w+\|?.*?\][+-]?.*$/gm)
const tagRegex = new RegExp(
/(?<=^| )#((?:[-_\p{L}\p{Emoji}\p{M}\d])+(?:\/[-_\p{L}\p{Emoji}\p{M}\d]+)*)/gu,
)
const blockReferenceRegex = new RegExp(/\^([-_A-Za-z0-9\u0400-\u04FF]+)$/g);
const blockReferenceRegex = new RegExp(/\^([-_A-Za-z0-9\u0400-\u04FF]+)$/g)
const ytLinkRegex = /^.*(youtu.be\/|v\/|u\/\w\/|embed\/|watch\?v=|\&v=)([^#\&\?]*).*/
const ytPlaylistLinkRegex = /[?&]list=([^#?&]*)/
const videoExtensionRegex = new RegExp(/\.(mp4|webm|ogg|avi|mov|flv|wmv|mkv|mpg|mpeg|3gp|m4v)$/)

File diff suppressed because one or more lines are too long

View File

@@ -118,7 +118,6 @@ a {
}
}
}
}
.flex-component {

View File

@@ -1,7 +1,7 @@
@use "./base.scss";
a[href^=http]:not([href*=garden\.struchkov\.dev]):not([href*=t\.me\/struchkov_dev]):after {
content: " ↗"
a[href^="http"]:not([href*="garden\.struchkov\.dev"]):not([href*="t\.me\/struchkov_dev"]):after {
content: " ↗";
}
article {
@@ -14,21 +14,21 @@ a.external {
}
a.internal {
border-radius: .1875rem;
padding: 0 .3rem;
border-radius: 0.1875rem;
padding: 0 0.3rem;
}
.recent-notes>ul.recent-ul>li .section>.desc>span>a {
.recent-notes > ul.recent-ul > li .section > .desc > span > a {
padding: 0;
background: none;
}
.search>#search-container {
.search > #search-container {
background-color: #23252f33;
backdrop-filter: blur(8px);
}
.backlinks>ul {
.backlinks > ul {
list-style: disc;
}
@@ -38,7 +38,7 @@ a.internal {
}
}
li.section-li>.section .meta {
li.section-li > .section .meta {
margin: 0;
}
@@ -81,13 +81,13 @@ article strong {
color: var(--secondary);
}
:not(pre)>code {
:not(pre) > code {
background: #e5eff5;
border: 1px solid var(--secondary);
border-radius: 6px;
color: #903;
font-size: .85em;
padding: .24rem .4rem .19rem;
font-size: 0.85em;
padding: 0.24rem 0.4rem 0.19rem;
text-shadow: none;
vertical-align: 0;
white-space: normal;
@@ -109,124 +109,124 @@ input[type="checkbox"] {
flex-direction: column;
overflow: hidden;
padding: 1rem;
position: relative
position: relative;
}
.notice.notice-telegram {
background-color: #5381bd
background-color: #5381bd;
}
.notice.notice-twitter {
background-color: #1da1f2
background-color: #1da1f2;
}
.notice.notice-comments {
background-color: #2c678d
background-color: #2c678d;
}
.notice.notice-donate {
background-color: #ee5162;
background-color: var(--notice-donate)
background-color: var(--notice-donate);
}
.notice__head {
align-items: center;
border: 1px dashed rgba(206,226,241,.85);
border: 1px dashed rgba(206, 226, 241, 0.85);
border-radius: 6px;
display: flex;
padding: .5rem 2rem
padding: 0.5rem 2rem;
}
.notice__head-icon {
color: #fff;
width: 1.25rem
width: 1.25rem;
}
.notice__head-text {
color: #fff;
font-size: .9375rem;
letter-spacing: .0625rem;
margin: 0 0 0 1rem
font-size: 0.9375rem;
letter-spacing: 0.0625rem;
margin: 0 0 0 1rem;
}
.kg-width-wide .notice__head-text {
font-size: 1.1rem
font-size: 1.1rem;
}
.notice__tail {
margin: .5rem 0 0
margin: 0.5rem 0 0;
}
.notice__tail-left {
margin: 0 .5rem
margin: 0 0.5rem;
}
.notice__tail-text {
color: #fff;
font-size: .9375rem;
letter-spacing: .03125rem
font-size: 0.9375rem;
letter-spacing: 0.03125rem;
}
.kg-width-wide .notice__tail-text {
font-size: 1.3rem
font-size: 1.3rem;
}
.notice__skin {
position: absolute;
right: 1rem;
top: 1rem
top: 1rem;
}
.notice__skin-icon {
color: rgba(206,226,241,.15);
width: 10rem
color: rgba(206, 226, 241, 0.15);
width: 10rem;
}
@media only screen and (min-width: 36em) {
.notice {
align-items:center;
flex-direction: row
align-items: center;
flex-direction: row;
}
}
@media only screen and (min-width: 48em) {
.notice {
padding:1rem 3rem
padding: 1rem 3rem;
}
.kg-width-wide .notice {
padding: 2rem 3rem
padding: 2rem 3rem;
}
}
@media only screen and (min-width: 36em) {
.notice__tail {
margin:0 0 0 1.25rem
margin: 0 0 0 1.25rem;
}
.notice__tail-left {
margin: 0 1.25rem 0 0
margin: 0 1.25rem 0 0;
}
.notice__tail-text {
font-size: 1.0625rem
font-size: 1.0625rem;
}
}
@media only screen and (min-width: 48em) {
.notice__skin {
right:3rem
right: 3rem;
}
}
@media (max-width: 700px) {
.notice__tail-left {
display:none
display: none;
}
}
@media (max-width: 980px) {
.footer-notice .notice {
border-radius:0
border-radius: 0;
}
}
}

View File

@@ -18,5 +18,5 @@
"jsxImportSource": "preact"
},
"include": ["**/*.ts", "**/*.tsx", "./package.json"],
"exclude": ["build/**/*.d.ts"]
"exclude": ["build/**/*.d.ts", "quartz/components/_SocialShare.tsx"]
}