Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
40 changes: 40 additions & 0 deletions php-transformer/src/HtmlToBlocks/HtmlCompilation.php
Original file line number Diff line number Diff line change
Expand Up @@ -9744,6 +9744,13 @@ public function convertLinkWrapperGroup(DOMElement $anchor, array &$fallbacks):
}

$linkAttrs = $this->linkPropagationAttributes($anchor);
// A gallery thumbnail wraps its image, and often a caption overlay, in
// a lightbox trigger. That link is the viewer, not a destination, so
// core's native lightbox replaces it rather than propagating an href
// that would navigate away from the page.
if ( $this->imageLinkOpensNativeLightbox($anchor) && $this->enableNativeLightboxOnImages($children) ) {
return $this->createBlock('core/group', $this->styleResolver->presentationAttributes($anchor), $children, $anchor);
}
if ( array() !== $linkAttrs && ! $this->propagateLinkWrapper($children, $linkAttrs) ) {
$this->recordDroppedLinkWrapper($anchor);
}
Expand Down Expand Up @@ -9902,6 +9909,39 @@ private function propagateLinkWrapper(array &$blocks, array $linkAttrs): bool
* @param array<string, mixed> $block
* @param array<string, string> $linkAttrs
*/
/**
* Opt every unlinked image inside a lightbox trigger into core's native
* lightbox. An image that already carries its own link keeps it, because
* core suppresses its lightbox when a link is present.
*
* @param array<int, array<string, mixed>> $blocks
*/
private function enableNativeLightboxOnImages(array &$blocks): bool
{
$enabled = false;
foreach ( $blocks as $index => $block ) {
if ( ! is_array($block) ) {
continue;
}

if ( 'core/image' === (string) ($block['blockName'] ?? '') ) {
$attrs = is_array($block['attrs'] ?? null) ? $block['attrs'] : array();
if ( '' === (string) ($attrs['href'] ?? '') ) {
$attrs['lightbox'] = array( 'enabled' => true );
$blocks[ $index ] = $this->rebuildBlock($block, $attrs);
$enabled = true;
}
continue;
}

if ( is_array($block['innerBlocks'] ?? null) && $this->enableNativeLightboxOnImages($blocks[ $index ]['innerBlocks']) ) {
$enabled = true;
}
}

return $enabled;
}

private function propagateLinkOntoImage(array &$block, array $linkAttrs): bool
{
$attrs = is_array($block['attrs'] ?? null) ? $block['attrs'] : array();
Expand Down
31 changes: 31 additions & 0 deletions php-transformer/tests/unit/image-lightbox-link-projection.php
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,37 @@
$nonImage
);

// A gallery card: the trigger wraps the image plus a caption overlay, so the
// link is propagated as a card-link wrapper rather than a bare image link.
$galleryCard = $transform(
'<main><div class="galleryInnerImageHolder">'
. '<a href="/uploads/img-1631_orig.jpeg" rel="lightbox[gallery219311460416557837]" title="Yosemite" class="w-fancybox">'
. '<img src="/media/img-1631.jpeg" class="galleryImage" width="800" height="600" alt="Yosemite">'
. '<div class="galleryCaptionHolder"><div class="galleryCaptionInnerText">Yosemite National Park, USA</div></div>'
. '</a></div></main>'
);
$assert(
str_contains($galleryCard, '"lightbox":{"enabled":true}'),
'a gallery card whose trigger also wraps a caption still opts into the native lightbox',
$galleryCard
);
$assert(
! str_contains($galleryCard, '"linkDestination"') && ! str_contains($galleryCard, 'href="/uploads/img-1631_orig.jpeg"'),
'the gallery card trigger link is not propagated onto the image',
$galleryCard
);

// A real card link wrapping an image plus copy keeps propagating its link.
$cardLink = $transform(
'<main><div><a href="/research.html"><img src="/media/thumb.jpg" width="800" height="600" alt="R">'
. '<div><p>Read the research</p></div></a></div></main>'
);
$assert(
! str_contains($cardLink, '"lightbox"') && str_contains($cardLink, '/research.html'),
'an ordinary card link keeps propagating its destination',
$cardLink
);

if ( 0 < $failures ) {
fwrite(STDERR, "image lightbox link projection FAILED: {$passes} passed, {$failures} failed\n");
exit(1);
Expand Down
Loading