perf: optimize loading timing for github cards and lightbox, clean up redundant head tags, and improve css organization

This commit is contained in:
radishzzz 2025-05-08 01:24:03 +01:00
parent d3c78a559a
commit d3d6561f4d
7 changed files with 124 additions and 110 deletions

View file

@ -4,54 +4,65 @@ function setupGithubCards() {
if (githubCards.length === 0) if (githubCards.length === 0)
return return
githubCards.forEach(async (card) => { const observer = new IntersectionObserver((entries) => {
const repo = (card as HTMLElement).dataset.repo entries.forEach((entry) => {
if (!repo) if (entry.isIntersecting) {
return loadCardData(entry.target as HTMLElement)
observer.unobserve(entry.target)
const avatarEl = card.querySelector('.gc-owner-avatar') as HTMLElement
const descEl = card.querySelector('.gc-repo-description') as HTMLElement
const starsEl = card.querySelector('.gc-stars-count') as HTMLElement
const forksEl = card.querySelector('.gc-forks-count') as HTMLElement
const licenseEl = card.querySelector('.gc-license-info') as HTMLElement
try {
const response = await fetch(`https://api.github.com/repos/${repo}`)
if (response.ok) {
const data = await response.json()
if (avatarEl && data.owner?.avatar_url)
avatarEl.style.backgroundImage = `url(${data.owner.avatar_url})`
if (descEl && data.description)
descEl.textContent = data.description
if (starsEl) {
starsEl.textContent = new Intl.NumberFormat('en', {
notation: 'compact',
maximumFractionDigits: 1,
}).format(data.stargazers_count)
}
if (forksEl) {
forksEl.textContent = new Intl.NumberFormat('en', {
notation: 'compact',
maximumFractionDigits: 1,
}).format(data.forks_count)
}
if (licenseEl)
licenseEl.textContent = data.license?.spdx_id || 'No License'
} }
else { })
if (descEl) }, { rootMargin: '200px' })
descEl.textContent = 'Loading failed.'
githubCards.forEach(card => observer.observe(card))
}
async function loadCardData(card: HTMLElement) {
const repo = card.dataset.repo
if (!repo)
return
const avatarEl = card.querySelector('.gc-owner-avatar') as HTMLElement
const descEl = card.querySelector('.gc-repo-description') as HTMLElement
const starsEl = card.querySelector('.gc-stars-count') as HTMLElement
const forksEl = card.querySelector('.gc-forks-count') as HTMLElement
const licenseEl = card.querySelector('.gc-license-info') as HTMLElement
try {
const response = await fetch(`https://api.github.com/repos/${repo}`)
if (response.ok) {
const data = await response.json()
if (avatarEl && data.owner?.avatar_url)
avatarEl.style.backgroundImage = `url(${data.owner.avatar_url})`
if (descEl && data.description)
descEl.textContent = data.description
if (starsEl) {
starsEl.textContent = new Intl.NumberFormat('en', {
notation: 'compact',
maximumFractionDigits: 1,
}).format(data.stargazers_count)
} }
if (forksEl) {
forksEl.textContent = new Intl.NumberFormat('en', {
notation: 'compact',
maximumFractionDigits: 1,
}).format(data.forks_count)
}
if (licenseEl)
licenseEl.textContent = data.license?.spdx_id || 'No License'
} }
catch { else {
console.error(`Failed to fetch ${repo}`) if (descEl)
descEl.textContent = 'Loading failed.'
} }
}) }
catch {
console.error(`Failed to fetch ${repo}`)
}
} }
setupGithubCards() setupGithubCards()

View file

@ -7,48 +7,62 @@ const pswp = import('photoswipe')
function setupPhotoSwipe() { function setupPhotoSwipe() {
const bodyElement = document.body const bodyElement = document.body
if (!bodyElement.hasAttribute('data-photoswipe-initialized')) { if (bodyElement.hasAttribute('data-photoswipe-initialized'))
lightbox = new PhotoSwipeLightbox({ return
gallery: 'article.heti img',
pswpModule: () => pswp,
bgOpacity: 0.9,
padding: {
top: window.innerHeight * 0.1,
bottom: window.innerHeight * 0.1,
left: window.innerWidth * 0.073,
right: window.innerWidth * 0.073,
},
zoom: false,
close: false,
wheelToZoom: true,
imageClickAction: 'close',
tapAction: 'close',
})
// Set image dimensions const images = document.querySelectorAll('article.heti img')
lightbox.addFilter('domItemData', (itemData, element) => { if (images.length === 0)
if (element instanceof HTMLImageElement) { return
// Set image source
itemData.src = element.src
// Set dimensions with fallback to window size lightbox = new PhotoSwipeLightbox({
itemData.w = Number(element.naturalWidth || window.innerWidth) gallery: 'article.heti img',
itemData.h = Number(element.naturalHeight || window.innerHeight) pswpModule: () => pswp,
bgOpacity: 0.9,
padding: {
top: window.innerHeight * 0.1,
bottom: window.innerHeight * 0.1,
left: window.innerWidth * 0.073,
right: window.innerWidth * 0.073,
},
zoom: false,
close: false,
wheelToZoom: true,
imageClickAction: 'close',
tapAction: 'close',
})
// Set thumbnail source // Set image dimensions
itemData.msrc = element.src lightbox.addFilter('domItemData', (itemData, element) => {
} if (element instanceof HTMLImageElement) {
return itemData // Set image source
}) itemData.src = element.src
lightbox.init() // Set dimensions with fallback to window size
itemData.w = Number(element.naturalWidth || window.innerWidth)
itemData.h = Number(element.naturalHeight || window.innerHeight)
bodyElement.setAttribute('data-photoswipe-initialized', 'true') // Set thumbnail source
itemData.msrc = element.src
}
return itemData
})
lightbox.init()
bodyElement.setAttribute('data-photoswipe-initialized', 'true')
}
function lazySetupPhotoSwipe() {
if ('requestIdleCallback' in window) {
window.requestIdleCallback(() => setupPhotoSwipe(), { timeout: 1000 })
}
else {
setTimeout(setupPhotoSwipe, 100)
} }
} }
setupPhotoSwipe() lazySetupPhotoSwipe()
document.addEventListener('astro:page-load', setupPhotoSwipe) document.addEventListener('astro:page-load', lazySetupPhotoSwipe)
</script> </script>
<style is:global> <style is:global>

View file

@ -21,7 +21,7 @@ const { mode, light: { background: lightMode }, dark: { background: darkMode } }
const { katex } = themeConfig.global const { katex } = themeConfig.global
const { verification = {}, twitterID = '', googleAnalyticsID = '', umamiAnalyticsID = '', apiflashKey = '' } = themeConfig.seo ?? {} const { verification = {}, twitterID = '', googleAnalyticsID = '', umamiAnalyticsID = '', apiflashKey = '' } = themeConfig.seo ?? {}
const { google = '', bing = '', yandex = '', baidu = '' } = verification const { google = '', bing = '', yandex = '', baidu = '' } = verification
const { commentURL = '', imageHostURL = '', customGoogleAnalyticsJS = '', customUmamiAnalyticsJS = '' } = themeConfig.preload const { commentURL = '', customGoogleAnalyticsJS = '', customUmamiAnalyticsJS = '' } = themeConfig.preload
const initMetaTheme = mode === 'dark' ? darkMode : lightMode const initMetaTheme = mode === 'dark' ? darkMode : lightMode
const siteTitle = i18nTitle ? currentUI.title : title const siteTitle = i18nTitle ? currentUI.title : title
@ -51,14 +51,12 @@ const pageImage = postSlug
<meta name="theme-color" content={initMetaTheme} /> <meta name="theme-color" content={initMetaTheme} />
<!-- Preload --> <!-- Preload -->
<link rel="preload" href="/font/Snell-Black.woff2" as="font" type="font/woff2" crossorigin />
<link rel="preload" href="/font/EarlySummer-Subset.woff2" as="font" type="font/woff2" crossorigin /> <link rel="preload" href="/font/EarlySummer-Subset.woff2" as="font" type="font/woff2" crossorigin />
<link rel="preload" href="/font/Snell-Black.woff2" as="font" type="font/woff2" crossorigin />
<link rel="preload" href="/font/Snell-Bold.woff2" as="font" type="font/woff2" crossorigin /> <link rel="preload" href="/font/Snell-Bold.woff2" as="font" type="font/woff2" crossorigin />
{katex && <link rel="stylesheet" href={katexCSS} />} {katex && <link rel="stylesheet" href={katexCSS} />}
{commentURL && <link rel="preconnect" href={commentURL} crossorigin />} {commentURL && <link rel="preconnect" href={commentURL} crossorigin />}
{commentURL && <link rel="dns-prefetch" href={commentURL} />} {commentURL && <link rel="dns-prefetch" href={commentURL} />}
{imageHostURL && <link rel="preconnect" href={imageHostURL} crossorigin />}
{imageHostURL && <link rel="dns-prefetch" href={imageHostURL} />}
<link rel="alternate" href="/rss.xml" type="application/rss+xml" title="RSS Feed" /> <link rel="alternate" href="/rss.xml" type="application/rss+xml" title="RSS Feed" />
<link rel="alternate" href="/atom.xml" type="application/atom+xml" title="Atom Feed" /> <link rel="alternate" href="/atom.xml" type="application/atom+xml" title="Atom Feed" />
<link rel="sitemap" href="/sitemap-index.xml" /> <link rel="sitemap" href="/sitemap-index.xml" />
@ -73,19 +71,14 @@ const pageImage = postSlug
/> />
))} ))}
<!-- Facebook Open Graph --> <!-- Open Graph -->
<meta property="og:type" content={postTitle ? 'article' : 'website'} /> <meta property="og:type" content={postTitle ? 'article' : 'website'} />
<meta property="og:url" content={Astro.url} /> <meta property="og:url" content={Astro.url} />
<meta property="og:title" content={pageTitle} /> <meta property="og:title" content={pageTitle} />
<meta property="og:description" content={pageDescription} /> <meta property="og:description" content={pageDescription} />
<meta property="og:image" content={pageImage} /> <meta property="og:image" content={pageImage} />
<!-- Twitter Card -->
<meta name="twitter:card" content="summary_large_image" /> <meta name="twitter:card" content="summary_large_image" />
{twitterID && <meta name="twitter:site" content={twitterID} />} {twitterID && <meta name="twitter:site" content={twitterID} />}
<!-- <meta name="twitter:title" content={pageTitle} />
<meta name="twitter:description" content={pageDescription} />
<meta name="twitter:image" content={pageImage} /> -->
<!-- Site Verification --> <!-- Site Verification -->
{google && <meta name="google-site-verification" content={google} />} {google && <meta name="google-site-verification" content={google} />}

View file

@ -49,9 +49,9 @@ const MarginBottom = isPost && themeConfig.comment?.enabled
</main> </main>
<Footer /> <Footer />
</div> </div>
{(isPost || isAbout) && <GithubCard />}
<Scrollbar />
<Button supportedLangs={supportedLangs} /> <Button supportedLangs={supportedLangs} />
<PhotoSwipe /> <Scrollbar />
{(isPost || isAbout) && <GithubCard />}
{(isPost || isAbout) && <PhotoSwipe />}
</body> </body>
</html> </html>

View file

@ -4,7 +4,15 @@
* 2. GitHub Card * 2. GitHub Card
*/ */
/* Admonition */ /* KaTeX Formula Overflow Fix */
.katex-display {
--at-apply: 'overflow-x-auto overflow-y-hidden scrollbar-hidden';
}
.katex-display::-webkit-scrollbar {
display: none;
}
/* Admonition >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> */
.admonition-title { .admonition-title {
--at-apply: 'flex items-center mb-4 font-semibold'; --at-apply: 'flex items-center mb-4 font-semibold';
} }
@ -121,6 +129,10 @@
} }
/* >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> */ /* >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> */
iframe {
--at-apply: 'mb-4 w-full aspect-video';
}
/* :where(details) { /* :where(details) {
--at-apply: 'my-4 px-4 py-3 border border-solid border-secondary/25 rounded cursor-pointer'; --at-apply: 'my-4 px-4 py-3 border border-solid border-secondary/25 rounded cursor-pointer';
} }

View file

@ -3,11 +3,9 @@
--uno-colors-secondary: theme('colors.secondary'); --uno-colors-secondary: theme('colors.secondary');
--uno-colors-background: theme('colors.background'); --uno-colors-background: theme('colors.background');
} }
html { html {
--at-apply: 'bg-background c-secondary antialiased'; --at-apply: 'bg-background c-secondary antialiased';
} }
/* Fix flash issue on iOS */ /* Fix flash issue on iOS */
body { body {
backface-visibility: hidden; backface-visibility: hidden;
@ -20,12 +18,10 @@ body {
clip-path: inset(0 0 0 0); clip-path: inset(0 0 0 0);
z-index: 99; z-index: 99;
} }
::view-transition-old(theme-transition) { ::view-transition-old(theme-transition) {
animation: none; animation: none;
z-index: -1; z-index: -1;
} }
@keyframes reveal { @keyframes reveal {
from { from {
clip-path: inset(var(--from)); clip-path: inset(var(--from));
@ -35,7 +31,6 @@ body {
html.dark { html.dark {
--from: 0 0 100% 0; --from: 0 0 100% 0;
} }
html:not(.dark) { html:not(.dark) {
--from: 100% 0 0 0; --from: 100% 0 0 0;
} }
@ -52,15 +47,13 @@ html[data-theme-transition] [data-disable-transition-on-theme] {
} }
} }
/* Import Custom Fonts >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> */ /* Snell Roundhand Static Font >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> */
/* Snell Roundhand Static Font */
@font-face { @font-face {
font-family: "Snell-Bold"; font-family: "Snell-Bold";
src: url("/font/Snell-Bold.woff2") format("woff2"); src: url("/font/Snell-Bold.woff2") format("woff2");
font-display: swap; font-display: swap;
unicode-range: U+0030-0039,U+0041-005A,U+0061-007A,U+00C1,U+00C9,U+00CD,U+00D3,U+00DA,U+00DC,U+00D1,U+00E1,U+00E9,U+00ED,U+00F3,U+00FA,U+00FC,U+00F1,U+0410-044F,U+0401,U+0451,U+0021-002F,U+003A-0040,U+00A9; unicode-range: U+0030-0039,U+0041-005A,U+0061-007A,U+00C1,U+00C9,U+00CD,U+00D3,U+00DA,U+00DC,U+00D1,U+00E1,U+00E9,U+00ED,U+00F3,U+00FA,U+00FC,U+00F1,U+0410-044F,U+0401,U+0451,U+0021-002F,U+003A-0040,U+00A9;
} }
@font-face { @font-face {
font-family: "Snell-Black"; font-family: "Snell-Black";
src: url("/font/Snell-Black.woff2") format("woff2"); src: url("/font/Snell-Black.woff2") format("woff2");
@ -76,7 +69,6 @@ html[data-theme-transition] [data-disable-transition-on-theme] {
font-weight: 400 700; font-weight: 400 700;
unicode-range: U+0030-0039,U+0041-005A,U+0061-007A,U+00C1,U+00C9,U+00CD,U+00D3,U+00DA,U+00DC,U+00D1,U+00E1,U+00E9,U+00ED,U+00F3,U+00FA,U+00FC,U+00F1,U+0410-044F,U+0401,U+0451,U+0021-002F,U+003A-0040,U+00A9; unicode-range: U+0030-0039,U+0041-005A,U+0061-007A,U+00C1,U+00C9,U+00CD,U+00D3,U+00DA,U+00DC,U+00D1,U+00E1,U+00E9,U+00ED,U+00F3,U+00FA,U+00FC,U+00F1,U+0410-044F,U+0401,U+0451,U+0021-002F,U+003A-0040,U+00A9;
} }
@font-face { @font-face {
font-family: "STIX-Italic"; font-family: "STIX-Italic";
src: url("/font/STIX-Italic.woff2") format("woff2-variations"); src: url("/font/STIX-Italic.woff2") format("woff2-variations");

View file

@ -15,15 +15,7 @@
/* Customized Post Title */ /* Customized Post Title */
.heti .post-title { .heti .post-title {
--at-apply: 'mb-2 text-8.6 font-bold leading-12 c-primary lg:text-9'; --at-apply: 'mb-2 text-8.6 c-primary font-bold leading-12 lg:text-9';
}
/* KaTeX Formula Overflow Fix */
.heti .katex-display {
--at-apply: 'overflow-x-auto overflow-y-hidden scrollbar-hidden';
}
.heti .katex-display::-webkit-scrollbar {
display: none;
} }
/* Headings */ /* Headings */