fix: complete mobile carousel and social updates

This commit is contained in:
Keith Solomon
2026-06-27 18:00:32 -05:00
parent f8d60a63a4
commit a360b8192a
14 changed files with 248 additions and 56 deletions
+1 -1
View File
@@ -110,7 +110,7 @@ $footerNav = ! empty( $locations['footer_navigation'] )
?> ?>
</div> </div>
<div class="copyright font-light text-cwc-blue-03/60 text-right py-3 text-12px"> <div class="copyright font-light text-white/70 text-right py-3 text-12px">
<?php <?php
if ( $copyright ) { if ( $copyright ) {
echo wp_kses_post( $copyright ); echo wp_kses_post( $copyright );
+3
View File
@@ -0,0 +1,3 @@
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M24 12.0301C24 5.38947 18.624 0 12 0C5.376 0 0 5.38947 0 12.0301C0 17.8526 4.128 22.7008 9.6 23.8195V15.6391H7.2V12.0301H9.6V9.02256C9.6 6.70075 11.484 4.81203 13.8 4.81203H16.8V8.42105H14.4C13.74 8.42105 13.2 8.96241 13.2 9.62406V12.0301H16.8V15.6391H13.2V24C19.26 23.3985 24 18.2737 24 12.0301Z" fill="white"/>
</svg>

After

Width:  |  Height:  |  Size: 425 B

+3
View File
@@ -0,0 +1,3 @@
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M12 0C5.3725 0 0 5.3725 0 12C0 18.6275 5.3725 24 12 24C18.6275 24 24 18.6275 24 12C24 5.3725 18.6275 0 12 0ZM9.0625 16.9738H6.6325V9.15375H9.0625V16.9738ZM7.8325 8.19375C7.065 8.19375 6.56875 7.65 6.56875 6.9775C6.56875 6.29125 7.08 5.76375 7.86375 5.76375C8.6475 5.76375 9.1275 6.29125 9.1425 6.9775C9.1425 7.65 8.6475 8.19375 7.8325 8.19375ZM17.9375 16.9738H15.5075V12.64C15.5075 11.6313 15.155 10.9462 14.2763 10.9462C13.605 10.9462 13.2063 11.41 13.03 11.8563C12.965 12.015 12.9488 12.24 12.9488 12.4638V16.9725H10.5175V11.6475C10.5175 10.6713 10.4862 9.855 10.4537 9.1525H12.565L12.6763 10.2388H12.725C13.045 9.72875 13.8288 8.97625 15.14 8.97625C16.7388 8.97625 17.9375 10.0475 17.9375 12.35V16.9738Z" fill="white"/>
</svg>

After

Width:  |  Height:  |  Size: 835 B

+3
View File
@@ -0,0 +1,3 @@
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M14.0037 11.7913L11.1963 10.4813C10.9513 10.3675 10.75 10.495 10.75 10.7662V13.2338C10.75 13.505 10.9513 13.6325 11.1963 13.5188L14.0025 12.2087C14.2488 12.0938 14.2487 11.9063 14.0037 11.7913ZM12 0C5.3725 0 0 5.3725 0 12C0 18.6275 5.3725 24 12 24C18.6275 24 24 18.6275 24 12C24 5.3725 18.6275 0 12 0ZM12 16.875C5.8575 16.875 5.75 16.3213 5.75 12C5.75 7.67875 5.8575 7.125 12 7.125C18.1425 7.125 18.25 7.67875 18.25 12C18.25 16.3213 18.1425 16.875 12 16.875Z" fill="white"/>
</svg>

After

Width:  |  Height:  |  Size: 587 B

+48
View File
@@ -0,0 +1,48 @@
const mobileViewport = window.matchMedia("(max-width: 640px)");
const initializeCarousel = (carousel) => {
const cards = Array.from(carousel.querySelectorAll(".recent-posts__card"));
const dots = Array.from(carousel.querySelectorAll(".recent-posts__dot"));
const previous = carousel.querySelector(".recent-posts__control--previous");
const next = carousel.querySelector(".recent-posts__control--next");
if (cards.length < 2 || !previous || !next) {
return;
}
let activeIndex = 0;
const render = () => {
cards.forEach((card, index) => {
const isActive = index === activeIndex;
card.classList.toggle("is-active", isActive);
card.hidden = mobileViewport.matches && !isActive;
});
dots.forEach((dot, index) => {
const isActive = index === activeIndex;
dot.classList.toggle("is-active", isActive);
dot.toggleAttribute("aria-current", isActive);
});
};
const showArticle = (index) => {
activeIndex = (index + cards.length) % cards.length;
render();
};
previous.addEventListener("click", () => showArticle(activeIndex - 1));
next.addEventListener("click", () => showArticle(activeIndex + 1));
dots.forEach((dot, index) =>
dot.addEventListener("click", () => showArticle(index)),
);
mobileViewport.addEventListener("change", render);
render();
};
const initRecentPostsCarousels = () => {
document.querySelectorAll(".recent-posts").forEach(initializeCarousel);
};
export default initRecentPostsCarousels;
+4
View File
@@ -7,6 +7,7 @@ import { registerBackToTopButton } from './components/backToTop.js';
import GetHeaderHeight from './modules/GetHeaderHeight.js'; import GetHeaderHeight from './modules/GetHeaderHeight.js';
import tagExternalLinks from './modules/TagExternalLinks.js'; import tagExternalLinks from './modules/TagExternalLinks.js';
import Navigation from './modules/Navigation.js'; import Navigation from './modules/Navigation.js';
import initRecentPostsCarousels from './modules/RecentPostsCarousel.js';
// Add passive event listeners // Add passive event listeners
! function (e) { ! function (e) {
@@ -68,6 +69,9 @@ document.addEventListener('DOMContentLoaded', () => {
// Initialize Header Height // Initialize Header Height
GetHeaderHeight(); GetHeaderHeight();
// Initialize mobile Recent Insights carousels.
initRecentPostsCarousels();
// Add Back to Top button to body // Add Back to Top button to body
// const backToTop = document.createElement('x-back-to-top'); // const backToTop = document.createElement('x-back-to-top');
// document.body.appendChild(backToTop); // document.body.appendChild(backToTop);
+1
View File
@@ -24,6 +24,7 @@
--color-primary-900: color-mix(in oklch, var(--color-primary) 90%, white); --color-primary-900: color-mix(in oklch, var(--color-primary) 90%, white);
--color-secondary: var(--color-cwc-orange-01); --color-secondary: var(--color-cwc-orange-01);
--color-secondary-accessible: #c43c2b;
--color-secondary-100: color-mix(in oklch, var(--color-secondary) 10%, white); --color-secondary-100: color-mix(in oklch, var(--color-secondary) 10%, white);
--color-secondary-200: color-mix(in oklch, var(--color-secondary) 20%, white); --color-secondary-200: color-mix(in oklch, var(--color-secondary) 20%, white);
--color-secondary-300: color-mix(in oklch, var(--color-secondary) 30%, white); --color-secondary-300: color-mix(in oklch, var(--color-secondary) 30%, white);
+3 -3
View File
@@ -143,10 +143,10 @@ x-button:has(.button[data-button-width="full"]) { @apply w-full; }
* like the ones below and changing the color values. * like the ones below and changing the color values.
*/ */
.btn[data-button-color="secondary"], .button[data-button-color="secondary"] { .btn[data-button-color="secondary"], .button[data-button-color="secondary"] {
--button-bg: var(--color-secondary); --button-bg: var(--color-secondary-accessible);
--button-color: var(--color-white); --button-color: var(--color-white);
--button-border-color: var(--color-secondary); --button-border-color: var(--color-secondary-accessible);
--button-outline-color: var(--color-secondary); --button-outline-color: var(--color-secondary-accessible);
--button-hover-bg: color-mix(in oklch, var(--color-secondary) 74%); --button-hover-bg: color-mix(in oklch, var(--color-secondary) 74%);
--button-hover-border-color: color-mix(in oklch, var(--color-secondary) 74%); --button-hover-border-color: color-mix(in oklch, var(--color-secondary) 74%);
--button-hover-color: var(--color-white); --button-hover-color: var(--color-white);
+47 -19
View File
@@ -1,58 +1,86 @@
const { test, expect } = require('@playwright/test'); const { test, expect } = require("@playwright/test");
const AxeBuilder = require('@axe-core/playwright').default; const AxeBuilder = require("@axe-core/playwright").default;
const domain = 'http://domain.local/'; const domain =
process.env.TEST_BASE_URL || "http://community-works-collaborative.test/";
test.use({ test.use({
viewport: { width: 1920, height: 1080 }, viewport: { width: 1920, height: 1080 },
}); });
test.describe('site-test', () => { test.describe("site-test", () => {
test('Homepage Test', async ({ page }, testInfo) => { test("Homepage Test", async ({ page }, testInfo) => {
await page.goto(domain); await page.goto(domain);
await page.screenshot({ path: 'test-results/homepage.png', fullPage: true }); await page.screenshot({
path: "test-results/homepage.png",
fullPage: true,
});
const accessibilityScanResults = await new AxeBuilder({ page }) const accessibilityScanResults = await new AxeBuilder({ page })
.withTags(['wcag2a', 'wcag2aa', 'wcag21a', 'wcag21aa', 'wcag22a', 'wcag22aa']) .withTags([
"wcag2a",
"wcag2aa",
"wcag21a",
"wcag21aa",
"wcag22a",
"wcag22aa",
])
.analyze(); .analyze();
await testInfo.attach('accessibility-scan-results', { await testInfo.attach("accessibility-scan-results", {
body: JSON.stringify(accessibilityScanResults, null, 2), body: JSON.stringify(accessibilityScanResults, null, 2),
contentType: 'application/json' contentType: "application/json",
}); });
expect(accessibilityScanResults.violations).toEqual([]); expect(accessibilityScanResults.violations).toEqual([]);
}); });
test('Blog Index Page Test', async ({ page }, testInfo) => { test("Blog Index Page Test", async ({ page }, testInfo) => {
await page.goto(`${domain}news/`); await page.goto(`${domain}news/`);
await page.screenshot({ path: 'test-results/blog-index.png', fullPage: true }); await page.screenshot({
path: "test-results/blog-index.png",
fullPage: true,
});
const accessibilityScanResults = await new AxeBuilder({ page }) const accessibilityScanResults = await new AxeBuilder({ page })
.withTags(['wcag2a', 'wcag2aa', 'wcag21a', 'wcag21aa', 'wcag22a', 'wcag22aa']) .withTags([
"wcag2a",
"wcag2aa",
"wcag21a",
"wcag21aa",
"wcag22a",
"wcag22aa",
])
.analyze(); .analyze();
await testInfo.attach('accessibility-scan-results', { await testInfo.attach("accessibility-scan-results", {
body: JSON.stringify(accessibilityScanResults, null, 2), body: JSON.stringify(accessibilityScanResults, null, 2),
contentType: 'application/json' contentType: "application/json",
}); });
expect(accessibilityScanResults.violations).toEqual([]); expect(accessibilityScanResults.violations).toEqual([]);
}); });
test('404 Page Test', async ({ page }, testInfo) => { test("404 Page Test", async ({ page }, testInfo) => {
await page.goto(`${domain}yaya/`); await page.goto(`${domain}yaya/`);
await page.screenshot({ path: 'test-results/404.png', fullPage: true }); await page.screenshot({ path: "test-results/404.png", fullPage: true });
const accessibilityScanResults = await new AxeBuilder({ page }) const accessibilityScanResults = await new AxeBuilder({ page })
.withTags(['wcag2a', 'wcag2aa', 'wcag21a', 'wcag21aa', 'wcag22a', 'wcag22aa']) .withTags([
"wcag2a",
"wcag2aa",
"wcag21a",
"wcag21aa",
"wcag22a",
"wcag22aa",
])
.analyze(); .analyze();
await testInfo.attach('accessibility-scan-results', { await testInfo.attach("accessibility-scan-results", {
body: JSON.stringify(accessibilityScanResults, null, 2), body: JSON.stringify(accessibilityScanResults, null, 2),
contentType: 'application/json' contentType: "application/json",
}); });
expect(accessibilityScanResults.violations).toEqual([]); expect(accessibilityScanResults.violations).toEqual([]);
+81 -8
View File
@@ -75,6 +75,11 @@
position: relative; position: relative;
} }
.recent-posts__controls,
.recent-posts__pagination {
display: none;
}
.recent-posts__grid::before { .recent-posts__grid::before {
background: var(--color-cwc-blue-03); background: var(--color-cwc-blue-03);
content: ""; content: "";
@@ -273,10 +278,57 @@
top: min(184px, calc(100cqw * 250 / 397)); top: min(184px, calc(100cqw * 250 / 397));
} }
.recent-posts__card:nth-child(n + 2) { .recent-posts__card {
display: none; display: none;
} }
.recent-posts__card.is-active {
display: flex;
}
.recent-posts__controls {
display: block;
}
.recent-posts__control {
align-items: center;
background: var(--color-secondary);
border: 0;
border-radius: 50%;
color: var(--color-white);
display: flex;
height: 3rem;
justify-content: center;
padding: 0;
position: absolute;
top: 10rem;
width: 3rem;
z-index: 3;
}
.recent-posts__control:hover,
.recent-posts__control:focus-visible {
background: var(--color-secondary-800);
}
.recent-posts__control svg {
fill: none;
height: 1.75rem;
stroke: currentColor;
stroke-linecap: round;
stroke-linejoin: round;
stroke-width: 2.5;
width: 1.75rem;
}
.recent-posts__control--previous {
left: -1.5rem;
}
.recent-posts__control--next {
right: -1.5rem;
}
.recent-posts__image-link { .recent-posts__image-link {
border-radius: 0.5rem 0.5rem 0 0; border-radius: 0.5rem 0.5rem 0 0;
} }
@@ -303,17 +355,38 @@
.recent-posts__footer { .recent-posts__footer {
align-items: center; align-items: center;
flex-direction: column; flex-direction: column;
gap: 1.25rem; margin-top: 1.25rem;
margin-top: 1.4rem;
} }
.recent-posts__footer::before { .recent-posts__pagination {
background: display: flex;
radial-gradient(circle, var(--color-cwc-blue-01) 0 0.2rem, transparent 0.22rem) left center / 0.75rem 0.5rem repeat-x; gap: 0.75rem;
justify-content: center;
margin-top: 1.5rem;
}
.recent-posts__dot {
align-items: center;
background: transparent;
border: 0;
display: flex;
height: 1.5rem;
justify-content: center;
padding: 0;
width: 1.5rem;
}
.recent-posts__dot::before {
background: var(--color-cwc-blue-01);
border-radius: 50%;
content: ""; content: "";
display: block;
height: 0.5rem; height: 0.5rem;
width: 2.25rem; opacity: 0.45;
width: 0.5rem;
}
.recent-posts__dot.is-active::before {
opacity: 1;
} }
.recent-posts__blog-link.button { .recent-posts__blog-link.button {
+31 -2
View File
@@ -56,13 +56,15 @@ $wrapper = blockWrapperAttributes( $classes, $is_preview );
<?php if ( $recent_posts->have_posts() ) : ?> <?php if ( $recent_posts->have_posts() ) : ?>
<div class="recent-posts__grid"> <div class="recent-posts__grid">
<?php <?php
$post_index = 0;
while ( $recent_posts->have_posts() ) : while ( $recent_posts->have_posts() ) :
$recent_posts->the_post(); $recent_posts->the_post();
$post_title = get_the_title(); $post_title = get_the_title();
$post_permalink = get_permalink(); $post_permalink = get_permalink();
$active_class = 0 === $post_index ? ' is-active' : '';
?> ?>
<article class="recent-posts__card"> <article class="recent-posts__card<?php echo esc_attr( $active_class ); ?>">
<?php /* translators: %s: Post title. */ ?> <?php /* translators: %s: Post title. */ ?>
<a class="recent-posts__image-link" href="<?php echo esc_url( $post_permalink ); ?>" aria-label="<?php echo esc_attr( sprintf( __( 'Continue reading %s', 'cwc' ), $post_title ) ); ?>"> <a class="recent-posts__image-link" href="<?php echo esc_url( $post_permalink ); ?>" aria-label="<?php echo esc_attr( sprintf( __( 'Continue reading %s', 'cwc' ), $post_title ) ); ?>">
<?php if ( has_post_thumbnail() ) : ?> <?php if ( has_post_thumbnail() ) : ?>
@@ -96,7 +98,34 @@ $wrapper = blockWrapperAttributes( $classes, $is_preview );
</a> </a>
</div> </div>
</article> </article>
<?php endwhile; ?> <?php
++$post_index;
endwhile;
?>
<div class="recent-posts__controls">
<button class="recent-posts__control recent-posts__control--previous" type="button" aria-label="<?php echo esc_attr__( 'Previous article', 'cwc' ); ?>">
<svg viewBox="0 0 24 24" aria-hidden="true" focusable="false">
<path d="M15 5 8 12l7 7" />
</svg>
</button>
<button class="recent-posts__control recent-posts__control--next" type="button" aria-label="<?php echo esc_attr__( 'Next article', 'cwc' ); ?>">
<svg viewBox="0 0 24 24" aria-hidden="true" focusable="false">
<path d="m9 5 7 7-7 7" />
</svg>
</button>
</div>
</div>
<div class="recent-posts__pagination" aria-label="<?php echo esc_attr__( 'Choose an article', 'cwc' ); ?>">
<?php for ( $dot_index = 0; $dot_index < $recent_posts->post_count; ++$dot_index ) : ?>
<button
class="recent-posts__dot<?php echo 0 === $dot_index ? ' is-active' : ''; ?>"
type="button"
aria-label="<?php echo esc_attr( sprintf( /* translators: %d: Article number. */ __( 'Show article %d', 'cwc' ), $dot_index + 1 ) ); ?>"
<?php echo 0 === $dot_index ? ' aria-current="true"' : ''; ?>
></button>
<?php endfor; ?>
</div> </div>
<?php wp_reset_postdata(); ?> <?php wp_reset_postdata(); ?>
+1 -1
View File
@@ -1 +1 @@
<i class="icon-facebook"></i> <img src="<?php echo esc_url( get_theme_file_uri( '/static/img/social-facebook.svg' ) ); ?>" alt="" width="24" height="24" aria-hidden="true" />
+1 -1
View File
@@ -1 +1 @@
<i class="icon-linkedin"></i> <img src="<?php echo esc_url( get_theme_file_uri( '/static/img/social-linkedin.svg' ) ); ?>" alt="" width="24" height="24" aria-hidden="true" />
+1 -1
View File
@@ -1 +1 @@
<i class="icon-youtube"></i> <img src="<?php echo esc_url( get_theme_file_uri( '/static/img/social-youtube.svg' ) ); ?>" alt="" width="24" height="24" aria-hidden="true" />