feat(extra-features): Made tab accordion and tabs

You can now choose between a bootstrap accordion style or the default tab style of products in the product details
This commit is contained in:
2026-06-25 15:25:58 +02:00
parent d280b8868a
commit b091468613
3 changed files with 202 additions and 89 deletions
@@ -0,0 +1,112 @@
{block name='product_tabs'}
<div id="accordion" class="product-tabs mt-2">
{* 1.) Attachments *}
{if $product.attachments}
<div class="card">
<div class="card-header bg-light p-0 rounded" id="headingAttachments">
<p class="mb-0 text-secondary">
<button class="btn btn-link w-100 text-left fw-600 accordion-item-btn" data-toggle="collapse" data-target="#collapseAttachments" aria-expanded="false" aria-controls="collapseAttachments">
<span class="text-secondary fw-700">
{l s='Attachments' d='Shop.Theme.Global'}
</span>
<span class="float-right accordion-icon">
{svg_icon file='plus.svg'}
</span>
</button>
</p>
</div>
<div id="collapseAttachments" class="collapse" aria-labelledby="headingAttachments" data-parent="#accordion">
<div class="card-body">
{foreach from=$product.attachments item=attachment}
<div class="attachment">
<h4><a href="{url entity='attachment' params=['id_attachment' => $attachment.id_attachment]}">{$attachment.name}</a></h4>
<p>{$attachment.description}</p>
<a href="{url entity='attachment' params=['id_attachment' => $attachment.id_attachment]}">
{l s='Download' d='Shop.Theme.Actions'} ({$attachment.file_size_formatted})
</a>
</div>
{/foreach}
</div>
</div>
</div>
{/if}
{* 2.) Description *}
{if $product.description }
<div class="card">
<div class="card-header bg-light p-0 rounded" id="headingDescription">
<p class="mb-0 text-secondary">
<button class="btn btn-link w-100 text-left fw-600 accordion-item-btn" data-toggle="collapse" data-target="#collapseDescription" aria-expanded="false" aria-controls="collapseDescription">
<span class="text-secondary fw-700">
{l s='Description' d='Shop.Theme.Global'}
</span>
<span class="float-right accordion-icon">
{svg_icon file='plus.svg'}
</span>
</button>
</p>
</div>
<div id="collapseDescription" class="collapse" aria-labelledby="headingDescription" data-parent="#accordion">
<div class="card-body">
{$product.description nofilter}
</div>
</div>
</div>
{/if}
{* 3.) extraContent *}
{if $product.extraContent}
<div class="card">
<div class="card-header bg-light p-0 rounded" id="headingextraContent">
<p class="mb-0 text-secondary">
<button class="btn btn-link w-100 text-left fw-600 accordion-item-btn" data-toggle="collapse" data-target="#collapseextraContent" aria-expanded="false" aria-controls="collapseextraContent">
<span class="text-secondary fw-700">
{l s='extraContent' d='Shop.Theme.Global'}
</span>
<span class="float-right accordion-icon">
{svg_icon file='plus.svg'}
</span>
</button>
</p>
</div>
<div id="collapseextraContent" class="collapse" aria-labelledby="headingextraContent" data-parent="#accordion">
<div class="card-body">
{foreach from=$product.extraContent item=extra key=extraKey}
<p>{$extra.title}</p>
<div>
{$extra.content nofilter}
</div>
{/foreach}
</div>
</div>
</div>
{/if}
{* 4.) Details *}
{capture name='product_details_content'}
{include file='catalog/_partials/product-details.tpl'}
{/capture}
{if $smarty.capture.product_details_content|strip|strlen > 0}
<div class="card">
<div class="card-header bg-light p-0 rounded" id="headingDetails">
<p class="mb-0 text-secondary">
<button class="btn btn-link w-100 text-left fw-600 accordion-item-btn" data-toggle="collapse" data-target="#collapseDetails" aria-expanded="false" aria-controls="collapseDetails">
<span class="text-secondary fw-700">
{l s='Product Details' d='Shop.Theme.Global'}
</span>
<span class="float-right accordion-icon">
{svg_icon file='plus.svg'}
</span>
</button>
</p>
</div>
<div id="collapseDetails" class="collapse" aria-labelledby="headingDetails" data-parent="#accordion">
<div class="card-body">
{$smarty.capture.product_details_content nofilter}
</div>
</div>
</div>
{/if}
</div>
{/block}
@@ -0,0 +1,89 @@
{block name='product_tabs'}
<div class="card product-tabs">
<div class="card-header">
<ul class="nav nav-tabs card-header-tabs" role="tablist">
{if $product.description}
<li class="nav-item">
<a
class="nav-link"
data-toggle="tab"
href="#description"
role="tab"
aria-controls="description"
>{l s='Description' d='Shop.Theme.Catalog'}</a>
</li>
{/if}
<li class="nav-item">
<a
class="nav-link"
data-toggle="tab"
href="#product-details"
role="tab"
aria-controls="product-details"
>{l s='Product Details' d='Shop.Theme.Catalog'}</a>
</li>
{if $product.attachments}
<li class="nav-item">
<a
class="nav-link"
data-toggle="tab"
href="#attachments"
role="tab"
aria-controls="attachments">{l s='Attachments' d='Shop.Theme.Catalog'}</a>
</li>
{/if}
{foreach from=$product.extraContent item=extra key=extraKey}
<li class="nav-item">
<a
class="nav-link"
data-toggle="tab"
href="#extra-{$extraKey}"
role="tab"
aria-controls="extra-{$extraKey}">{$extra.title}</a>
</li>
{/foreach}
</ul>
</div>
<div class="card-body">
<div class="tab-content" id="tab-content">
<div class="tab-pane fade in" id="description" role="tabpanel">
{block name='product_description'}
{cms_images_block webpEnabled=$webpEnabled}
<div class="product-description cms-content">{$product.description nofilter}</div>
{/cms_images_block}
{/block}
</div>
{block name='product_details'}
{include file='catalog/_partials/product-details.tpl'}
{/block}
{block name='product_attachments'}
{if $product.attachments}
<div class="tab-pane fade in" id="attachments" role="tabpanel">
<section class="product-attachments">
<p class="h5 text-uppercase">{l s='Download' d='Shop.Theme.Actions'}</p>
{foreach from=$product.attachments item=attachment}
<div class="attachment">
<h4><a href="{url entity='attachment' params=['id_attachment' => $attachment.id_attachment]}">{$attachment.name}</a></h4>
<p>{$attachment.description}</p>
<a href="{url entity='attachment' params=['id_attachment' => $attachment.id_attachment]}">
{l s='Download' d='Shop.Theme.Actions'} ({$attachment.file_size_formatted})
</a>
</div>
{/foreach}
</section>
</div>
{/if}
{/block}
{foreach from=$product.extraContent item=extra key=extraKey}
<div class="tab-pane fade in {$extra.attr.class} cms-content" id="extra-{$extraKey}" role="tabpanel" {foreach $extra.attr as $key => $val} {$key}="{$val}"{/foreach}>
{$extra.content nofilter}
</div>
{/foreach}
</div>
</div>
</div>
{/block}
@@ -1,89 +1 @@
{block name='product_tabs'} {include file="catalog/_partials/product-tabs-accordion.tpl"}
<div class="card product-tabs">
<div class="card-header">
<ul class="nav nav-tabs card-header-tabs" role="tablist">
{if $product.description}
<li class="nav-item">
<a
class="nav-link"
data-toggle="tab"
href="#description"
role="tab"
aria-controls="description"
>{l s='Description' d='Shop.Theme.Catalog'}</a>
</li>
{/if}
<li class="nav-item">
<a
class="nav-link"
data-toggle="tab"
href="#product-details"
role="tab"
aria-controls="product-details"
>{l s='Product Details' d='Shop.Theme.Catalog'}</a>
</li>
{if $product.attachments}
<li class="nav-item">
<a
class="nav-link"
data-toggle="tab"
href="#attachments"
role="tab"
aria-controls="attachments">{l s='Attachments' d='Shop.Theme.Catalog'}</a>
</li>
{/if}
{foreach from=$product.extraContent item=extra key=extraKey}
<li class="nav-item">
<a
class="nav-link"
data-toggle="tab"
href="#extra-{$extraKey}"
role="tab"
aria-controls="extra-{$extraKey}">{$extra.title}</a>
</li>
{/foreach}
</ul>
</div>
<div class="card-body">
<div class="tab-content" id="tab-content">
<div class="tab-pane fade in" id="description" role="tabpanel">
{block name='product_description'}
{cms_images_block webpEnabled=$webpEnabled}
<div class="product-description cms-content">{$product.description nofilter}</div>
{/cms_images_block}
{/block}
</div>
{block name='product_details'}
{include file='catalog/_partials/product-details.tpl'}
{/block}
{block name='product_attachments'}
{if $product.attachments}
<div class="tab-pane fade in" id="attachments" role="tabpanel">
<section class="product-attachments">
<p class="h5 text-uppercase">{l s='Download' d='Shop.Theme.Actions'}</p>
{foreach from=$product.attachments item=attachment}
<div class="attachment">
<h4><a href="{url entity='attachment' params=['id_attachment' => $attachment.id_attachment]}">{$attachment.name}</a></h4>
<p>{$attachment.description}</p>
<a href="{url entity='attachment' params=['id_attachment' => $attachment.id_attachment]}">
{l s='Download' d='Shop.Theme.Actions'} ({$attachment.file_size_formatted})
</a>
</div>
{/foreach}
</section>
</div>
{/if}
{/block}
{foreach from=$product.extraContent item=extra key=extraKey}
<div class="tab-pane fade in {$extra.attr.class} cms-content" id="extra-{$extraKey}" role="tabpanel" {foreach $extra.attr as $key => $val} {$key}="{$val}"{/foreach}>
{$extra.content nofilter}
</div>
{/foreach}
</div>
</div>
</div>
{/block}