Fix flash of white theme on page navigation
Add inline script in <head> that applies theme/accent preferences immediately before body renders, preventing FOUC when navigating between pages in dark mode.
This commit is contained in:
parent
eca412bc28
commit
a216576054
12
src/Makefile
12
src/Makefile
@ -26,7 +26,7 @@ SITE_DIST = dist/site
|
||||
AWK_UTIL = awk '/^\s*\[[0-9]+\]\s+([^\.].+)/ {print $$2}'
|
||||
AWK_UTIL_NOCRLF = awk '/^\s*\[[0-9]+\]\s+([^\.].+)/ {printf $$2" "}'
|
||||
|
||||
PANDOC_ARGS = --standalone --table-of-contents --section-divs --email-obfuscation=references --css="/main.css" --include-after-body=$(RAW_DIST)/footer.html --include-after-body=$(RAW_DIST)/scripts.html
|
||||
PANDOC_ARGS = --standalone --table-of-contents --section-divs --email-obfuscation=references --css="/main.css" --include-in-header=$(RAW_DIST)/head.html --include-after-body=$(RAW_DIST)/footer.html --include-after-body=$(RAW_DIST)/scripts.html
|
||||
|
||||
PYTHON = $(shell which python3)
|
||||
|
||||
@ -49,7 +49,15 @@ libdzonerzy:
|
||||
|
||||
libdzonerzy-dump:
|
||||
$(READELF) -S -W $(DIST)/$(OUTPUT) | $(AWK_UTIL) | xargs dirname {} | sort | uniq | xargs -I{} mkdir -p $(RAW_DIST)/{}
|
||||
@$(foreach fn, $(shell $(READELF) -S -W $(DIST)/$(OUTPUT) | $(AWK_UTIL_NOCRLF)), $(OBJCOPY) $(DIST)/$(OUTPUT) --dump-section $(fn)=/dev/stdout | cat | head -c -1 > $(RAW_DIST)/$(fn);)
|
||||
@$(foreach fn, $(shell $(READELF) -S -W $(DIST)/$(OUTPUT) | $(AWK_UTIL_NOCRLF)), \
|
||||
if echo "$(fn)" | grep -qE '^(articles|pages|advisory)/'; then \
|
||||
size=$$($(OBJCOPY) $(DIST)/$(OUTPUT) --dump-section $(fn)=/dev/stdout | head -c 4 | od -An -tu1 | awk '{print $$1 + $$2*256 + $$3*65536 + $$4*16777216}'); \
|
||||
$(OBJCOPY) $(DIST)/$(OUTPUT) --dump-section $(fn)=/dev/stdout | tail -c +5 | head -c $$size > $(RAW_DIST)/$(fn); \
|
||||
elif echo "$(fn)" | grep -qE '^embed/'; then \
|
||||
$(OBJCOPY) $(DIST)/$(OUTPUT) --dump-section $(fn)=/dev/stdout > $(RAW_DIST)/$(fn); \
|
||||
else \
|
||||
$(OBJCOPY) $(DIST)/$(OUTPUT) --dump-section $(fn)=/dev/stdout | tr -d '\000' > $(RAW_DIST)/$(fn); \
|
||||
fi;)
|
||||
|
||||
libdzonerzy-gen: libdzonerzy-dump
|
||||
@mkdir -p $(SITE_DIST)/assets/
|
||||
|
||||
@ -679,6 +679,18 @@ Copyright:
|
||||
" .accent-picker { right: 2.75rem; }\\n" \
|
||||
"}\\n"
|
||||
|
||||
#define HEAD_HTML \
|
||||
HTML_TAG_OPEN("script", "") \
|
||||
HTML_RAWTEXT("(function(){") \
|
||||
HTML_RAWTEXT("var t=localStorage.getItem('theme-preference');") \
|
||||
HTML_RAWTEXT("var a=localStorage.getItem('accent-preference');") \
|
||||
HTML_RAWTEXT("if(!t)t=window.matchMedia('(prefers-color-scheme:dark)').matches?'dark':'light';") \
|
||||
HTML_RAWTEXT("if(t==='dark')document.documentElement.classList.add('dark');") \
|
||||
HTML_RAWTEXT("if(a&&a!=='blue')document.documentElement.classList.add('accent-'+a);") \
|
||||
HTML_RAWTEXT("})();") \
|
||||
HTML_TAG_CLOSE("script") \
|
||||
HTML_NEWLINE()
|
||||
|
||||
#define FOOTER_HTML \
|
||||
MD_RAWTAG("footer", "" \
|
||||
"<span>" \
|
||||
@ -926,6 +938,8 @@ SECTION("footer.html")
|
||||
static const char footerhtml[] = FOOTER_HTML;
|
||||
SECTION("scripts.html")
|
||||
static const char scriptshtml[] = SCRIPTS_HTML;
|
||||
SECTION("head.html")
|
||||
static const char headhtml[] = HEAD_HTML;
|
||||
SECTION("main.js")
|
||||
static const char mainjs[] = MAIN_JS;
|
||||
SECTION("sitemap.xml")
|
||||
|
||||
@ -253,13 +253,14 @@ unsigned char *read_file_data(FILE *f, size_t *size)
|
||||
*size = ftell(f);
|
||||
fseek(f, 0, SEEK_SET);
|
||||
|
||||
unsigned char *data = malloc(*size);
|
||||
unsigned char *data = malloc(*size + 1);
|
||||
if (data == NULL)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
fread(data, 1, *size, f);
|
||||
data[*size] = '\0'; // null-terminate for string operations
|
||||
|
||||
return data;
|
||||
}
|
||||
@ -468,15 +469,25 @@ int embed(embed_t *args)
|
||||
data = data_updated;
|
||||
}
|
||||
|
||||
// Prepend 4-byte size (little-endian) for non-embed types
|
||||
int has_size_prefix = (args->type != TYPE_EMBED);
|
||||
|
||||
if (args->autowrap)
|
||||
{
|
||||
fprintf(output, " ");
|
||||
|
||||
// Write 4-byte size prefix (little-endian)
|
||||
if (has_size_prefix)
|
||||
{
|
||||
fprintf(output, "0x%02X, 0x%02X, 0x%02X, 0x%02X, ",
|
||||
(unsigned char)(size & 0xFF),
|
||||
(unsigned char)((size >> 8) & 0xFF),
|
||||
(unsigned char)((size >> 16) & 0xFF),
|
||||
(unsigned char)((size >> 24) & 0xFF));
|
||||
}
|
||||
|
||||
while (i < size)
|
||||
{
|
||||
if (i == 0)
|
||||
{
|
||||
fprintf(output, " ");
|
||||
}
|
||||
|
||||
fprintf(output, "0x%02X", data[i]);
|
||||
|
||||
if (i % 16 == 15)
|
||||
@ -497,13 +508,20 @@ int embed(embed_t *args)
|
||||
fprintf(output, "\n");
|
||||
}
|
||||
|
||||
if (args->type == TYPE_EMBED)
|
||||
fprintf(output, " 0x00,\n");
|
||||
|
||||
fprintf(output, "};\n");
|
||||
}
|
||||
else
|
||||
{
|
||||
// Write 4-byte size prefix (little-endian)
|
||||
if (has_size_prefix)
|
||||
{
|
||||
fprintf(output, "0x%02X, 0x%02X, 0x%02X, 0x%02X, ",
|
||||
(unsigned char)(size & 0xFF),
|
||||
(unsigned char)((size >> 8) & 0xFF),
|
||||
(unsigned char)((size >> 16) & 0xFF),
|
||||
(unsigned char)((size >> 24) & 0xFF));
|
||||
}
|
||||
|
||||
while (i < size)
|
||||
{
|
||||
// no wrap
|
||||
@ -519,9 +537,6 @@ int embed(embed_t *args)
|
||||
i++;
|
||||
}
|
||||
|
||||
if (args->type == TYPE_EMBED)
|
||||
fprintf(output, ", 0x00");
|
||||
|
||||
fprintf(output, "};\n\n");
|
||||
}
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user