refactor: render CV only on /cv path and remove toggle
Co-authored-by: aider (openai/qwen3.6) <aider@aider.chat>
This commit is contained in:
parent
597b673958
commit
7c009ee851
108
index.php
108
index.php
@ -5,6 +5,8 @@
|
|||||||
*/
|
*/
|
||||||
$cvData = json_decode(file_get_contents(__DIR__ . '/cv.json'), true);
|
$cvData = json_decode(file_get_contents(__DIR__ . '/cv.json'), true);
|
||||||
|
|
||||||
|
$isCvPath = strpos($_SERVER['REQUEST_URI'], '/cv') !== false;
|
||||||
|
|
||||||
$name = $cvData['name'] ?? '';
|
$name = $cvData['name'] ?? '';
|
||||||
$headline = $cvData['headline'] ?? '';
|
$headline = $cvData['headline'] ?? '';
|
||||||
$summary = $cvData['summary'] ?? '';
|
$summary = $cvData['summary'] ?? '';
|
||||||
@ -222,23 +224,14 @@ $cv_skills = $cvData['skills'] ?? [];
|
|||||||
</section>
|
</section>
|
||||||
<?php endif; ?>
|
<?php endif; ?>
|
||||||
|
|
||||||
|
<?php if ($isCvPath): ?>
|
||||||
<section class="card cv-container">
|
<section class="card cv-container">
|
||||||
<label class="cv-header" for="cv-toggle">
|
|
||||||
<div class="cv-toggle-container">
|
|
||||||
<span id="toggle-label-text">Looking to hire?</span>
|
|
||||||
<span class="switch">
|
|
||||||
<input type="checkbox" id="cv-toggle">
|
|
||||||
<span class="slider"></span>
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
</label>
|
|
||||||
|
|
||||||
<div class="cv-content">
|
<div class="cv-content">
|
||||||
<?php
|
<?php
|
||||||
$firstJob = $cv_experience[0] ?? null;
|
$firstJob = $cv_experience[0] ?? null;
|
||||||
if ($firstJob):
|
if ($firstJob):
|
||||||
?>
|
?>
|
||||||
<section class="cv-section first-experience hidden hidden-toggle">
|
<section class="cv-section first-experience">
|
||||||
<h2>Latest Experience</h2>
|
<h2>Latest Experience</h2>
|
||||||
<article class="cv-item">
|
<article class="cv-item">
|
||||||
<header class="cv-item-header">
|
<header class="cv-item-header">
|
||||||
@ -250,7 +243,7 @@ $cv_skills = $cvData['skills'] ?? [];
|
|||||||
</article>
|
</article>
|
||||||
</section>
|
</section>
|
||||||
<?php endif; ?>
|
<?php endif; ?>
|
||||||
<section class="cv-section skills hidden hidden-toggle">
|
<section class="cv-section skills">
|
||||||
<h2>Skills</h2>
|
<h2>Skills</h2>
|
||||||
<div class="skill-categories">
|
<div class="skill-categories">
|
||||||
<?php
|
<?php
|
||||||
@ -272,7 +265,7 @@ $cv_skills = $cvData['skills'] ?? [];
|
|||||||
</div>
|
</div>
|
||||||
</section>
|
</section>
|
||||||
|
|
||||||
<section class="cv-section experience hidden hidden-toggle">
|
<section class="cv-section experience">
|
||||||
<h2>Past Experience</h2>
|
<h2>Past Experience</h2>
|
||||||
<?php foreach (array_slice($cv_experience, 1) as $job): ?>
|
<?php foreach (array_slice($cv_experience, 1) as $job): ?>
|
||||||
<article class="cv-item">
|
<article class="cv-item">
|
||||||
@ -286,7 +279,7 @@ $cv_skills = $cvData['skills'] ?? [];
|
|||||||
<?php endforeach; ?>
|
<?php endforeach; ?>
|
||||||
</section>
|
</section>
|
||||||
|
|
||||||
<section class="cv-section education hidden hidden-toggle">
|
<section class="cv-section education">
|
||||||
<h2>Education</h2>
|
<h2>Education</h2>
|
||||||
<?php foreach ($cv_education as $edu): ?>
|
<?php foreach ($cv_education as $edu): ?>
|
||||||
<article class="cv-item">
|
<article class="cv-item">
|
||||||
@ -303,6 +296,7 @@ $cv_skills = $cvData['skills'] ?? [];
|
|||||||
</section>
|
</section>
|
||||||
</div>
|
</div>
|
||||||
</section>
|
</section>
|
||||||
|
<?php endif; ?>
|
||||||
</main>
|
</main>
|
||||||
|
|
||||||
<script>
|
<script>
|
||||||
@ -312,95 +306,9 @@ $cv_skills = $cvData['skills'] ?? [];
|
|||||||
if (el) el.innerHTML = `<a href="mailto:${addr}">${addr}</a>`;
|
if (el) el.innerHTML = `<a href="mailto:${addr}">${addr}</a>`;
|
||||||
})('<?= base64_encode($email_user) ?>', 'dejvino', 'cz');
|
})('<?= base64_encode($email_user) ?>', 'dejvino', 'cz');
|
||||||
|
|
||||||
const animationDuration = 500; // Matches CSS animation duration (0.5s)
|
|
||||||
const staggerDelay = 200; // Delay between each panel unrolling (ms)
|
|
||||||
|
|
||||||
const toggleCV = (show, updateUrl = true, animate = true) => {
|
|
||||||
const grid = document.querySelector('.bento-grid');
|
|
||||||
const labelText = document.getElementById('toggle-label-text');
|
|
||||||
|
|
||||||
if (labelText) labelText.innerText = show ? 'Here is my Resume' : 'Looking to hire?';
|
|
||||||
|
|
||||||
const cvPanels = Array.from(document.querySelectorAll('.hidden-toggle')).filter(el => el);
|
|
||||||
|
|
||||||
if (show) {
|
|
||||||
grid.classList.add('cv-mode');
|
|
||||||
|
|
||||||
cvPanels.forEach((el, index) => {
|
|
||||||
const reveal = () => {
|
|
||||||
el.classList.remove('hidden', 'fade-out', 'reveal');
|
|
||||||
void el.offsetWidth; // Force reflow
|
|
||||||
el.classList.add('reveal');
|
|
||||||
};
|
|
||||||
if (animate) setTimeout(reveal, index * staggerDelay);
|
|
||||||
else reveal();
|
|
||||||
});
|
|
||||||
} else {
|
|
||||||
const panels = [...cvPanels].reverse();
|
|
||||||
panels.forEach((el, index) => {
|
|
||||||
const hide = () => {
|
|
||||||
el.classList.remove('reveal');
|
|
||||||
if (animate) {
|
|
||||||
el.classList.add('fade-out');
|
|
||||||
setTimeout(() => {
|
|
||||||
el.classList.add('hidden');
|
|
||||||
el.classList.remove('fade-out');
|
|
||||||
}, animationDuration);
|
|
||||||
} else {
|
|
||||||
el.classList.add('hidden');
|
|
||||||
}
|
|
||||||
};
|
|
||||||
if (animate) setTimeout(hide, index * staggerDelay);
|
|
||||||
else hide();
|
|
||||||
});
|
|
||||||
|
|
||||||
if (animate) {
|
|
||||||
// Remove cv-mode only after the longest-running shrink animation finishes
|
|
||||||
const totalRollupTime = (cvPanels.length * staggerDelay) + animationDuration;
|
|
||||||
setTimeout(() => grid.classList.remove('cv-mode'), totalRollupTime);
|
|
||||||
} else {
|
|
||||||
grid.classList.remove('cv-mode');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (updateUrl) {
|
|
||||||
const newUrl = show ? '/cv' : '/';
|
|
||||||
history.pushState({ cv: show }, '', newUrl);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Keep toggle in sync
|
|
||||||
const toggle = document.getElementById('cv-toggle');
|
|
||||||
if (toggle) toggle.checked = show;
|
|
||||||
};
|
|
||||||
|
|
||||||
// Initialize state from URL
|
|
||||||
const isCvPath = window.location.pathname.includes('/cv');
|
|
||||||
const checkUrl = (animate = false) => toggleCV(isCvPath, false, animate);
|
|
||||||
|
|
||||||
window.addEventListener('load', () => {
|
window.addEventListener('load', () => {
|
||||||
checkUrl(false);
|
|
||||||
// Small delay to ensure initial styles are applied before enabling transitions
|
|
||||||
setTimeout(() => document.body.classList.remove('preload'), 20);
|
setTimeout(() => document.body.classList.remove('preload'), 20);
|
||||||
});
|
});
|
||||||
|
|
||||||
// Handle back/forward navigation
|
|
||||||
window.addEventListener('popstate', () => {
|
|
||||||
const showCv = window.location.pathname.includes('/cv');
|
|
||||||
toggleCV(showCv, false, true);
|
|
||||||
});
|
|
||||||
|
|
||||||
const cvToggleInput = document.getElementById('cv-toggle');
|
|
||||||
cvToggleInput?.addEventListener('change', (e) => {
|
|
||||||
toggleCV(e.target.checked);
|
|
||||||
|
|
||||||
// Only scroll to top if we are collapsing the CV and the user is scrolled down
|
|
||||||
if (!e.target.checked && window.scrollY > 200) {
|
|
||||||
window.scrollTo({
|
|
||||||
top: document.querySelector('.cv-container').offsetTop - 20,
|
|
||||||
behavior: 'smooth'
|
|
||||||
});
|
|
||||||
}
|
|
||||||
});
|
|
||||||
</script>
|
</script>
|
||||||
<!-- Cloudflare Web Analytics -->
|
<!-- Cloudflare Web Analytics -->
|
||||||
<script defer src='https://static.cloudflareinsights.com/beacon.min.js' data-cf-beacon='{"token": "90827cb740cd4b1db611be059f64daa9"}'></script><!-- End Cloudflare Web Analytics -->
|
<script defer src='https://static.cloudflareinsights.com/beacon.min.js' data-cf-beacon='{"token": "90827cb740cd4b1db611be059f64daa9"}'></script><!-- End Cloudflare Web Analytics -->
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user