Read data from extended table in a template - twig

I have a question about shopware 6.
I have created an extra table for my property_group options, called property_group_extension.
So I have extended this table in my theme:
class PropertyGroupExtension extends EntityExtension
{
public function extendFields(FieldCollection $collection): void
{
$collection->add(
new OneToOneAssociationField('property_group_extension', 'id', 'property_group_id', PropertyGroupExtensionDefinition::class, true)
);
}
public function getDefinitionClass(): string
{
return PropertyGroupDefinition::class;
}
}
But how can I call this extra db-table property_group_extension (with a column test) in my twig template?
This is NOT working:
properties.html.twig:
{% for group in page.product.sortedProperties %}
{% block page_product_detail_properties_table_row %}
<tr class="properties-row">
{% block page_product_detail_properties_item_label %}
<th class="properties-label">
{{ group.test }} - {# <= HOW CAN I INSERT HERE MY TEST COLUMN??? #}
{{ group.translated.name|e }}:
</th>
{% endblock %}
{% block page_product_detail_properties_item_value %}
<td class="properties-value">
{% apply spaceless %}
{% for option in group.options %}
{% set i = ( i | default(0) ) + 1 %}
<span>{% if i > 1 %}, {% endif %}{{ option.translated.name|e }}</span>
{% endfor %}
{% endapply %}
</td>
{% endblock %}
</tr>
{% endblock %}
{% endfor %}

I believe, the data does not automatically populate to the data structures in the twig by adding an extension.
You usually would hook into an even that is triggered for the page you want to access the data in.
Next you add an extension to the result so it is accessible in the twig template.

Related

Iterating over Shopware Array and trying to get the key not working

Hey iam currently trying to get the description of the first menu navigation in Shopware 6.
For that i use the array page.header.navigation.active.breadcrumb and use its key in page.header.navigation.tree[key].description, but my key value is empty.
Thats happening due to the key beeing empty for no reason.
Heres my Code:
{% sw_extends "#Storefront/storefront/section/cms-section-sidebar.html.twig" %}
{% set topMenu = null %}
{% for key, value in page.header.navigation.active.breadcrumb %}
{% if loop.index == 2 %}
{% set topMenu = value %}
{# {% set topMenuDescription = page.header.navigation.tree[key].category.description %} #}
{% set topMenuDescription = key %}
{% endif %}
{% endfor %}
{% set currentMenu = page.header.navigation.active.breadcrumb | last %}
{# {% set currentMenu = page.header.navigation.active.name %} #}
{# {% set topMenuDescription = page.header.navigation.active.description %} #}
{# {% if ! topMenuDescription %}
{% set topMenuDescription = page.header.navigation.active.description %}
{% endif %} #}
{% block section_main_content_block %}
<div class="category-top">
<div class="category-banner">
<img src="/media/6a/fd/8b/1632946677/listing-banner.jpg">
<div class="category-banner-headlines">
{% if (currentMenu != topMenu) %}
<h3>{{ topMenu }}<h3>
<h2>{{ currentMenu }}<h2>
{% else %}
<h2 class="sameMenu">{{ currentMenu }}<h2>
{% endif %}
</div>
</div>
<div class="category-description">
<h1>{{ currentMenu }}</h1>
{{ topMenuDescription | trans | raw }}
</div>
</div>
{{ parent() }}
{% endblock %}
Also here is the structure of the key i want to get:
key-i-want-to-get
And heres the description i want to get:
description-i-want-to-get
Sidenote: The description in my example is empty, since i do the showcase in a seperate testing area, where i havent set a description
The reason topMenuDescription is empty is because the variable only exist inside the scope of the {% for %}-loop you've created. Outside this loop the variable doesn't exist.
In order to solve this issue you need to alter the scope of topMenuDescription by defining the variable outside the {% for %}-loop
{% set topMenuDescription = null %}
{% for key, value in page.header.navigation.active.breadcrumb %}
{% if loop.index == 2 %}
{% set topMenu = value %}
{# {% set topMenuDescription = page.header.navigation.tree[key].category.description %} #}
{% set topMenuDescription = key %}
{% endif %}
{% endfor %}
sidenote
You really should enable twig's debug whilst developing as your current snippet would throw a RuntimeError explaining the variable does not exist.

How to filter out the order status in frontend at orders overview in shopware6

I am trying to filter the order status depending on the orderstatus at frontend.
enter code here
{% block page_account_orders_overview %}
<div class="account-orders-overview">
{% block page_account_orders_table %}
{% block page_account_orders_table_body %}
{% for order in page.orders %}
{% set orderState = order.stateMachineState.technicalName %}
{% if order.type == in_progress %}
<div class="table order-table"
data-order-detail-loader="true">
{% sw_include '#Storefront/storefront/page/account/quotationorder-history/quotationorder-item.html.twig' %}
</div>
{% endif %}
{% endfor %}
{% endblock %}
{% endblock %}
</div>
{% endblock %}
You need to add quotes to a string comparison:
{% if order.type == "in_progress" %}

How to reduce duplication in Twig template

I have an if/else condition in a twig template which switches the out tag of a block of code, however the inner block is the same. Is there a way to reduce the duplication without creating a separate file?
This is what I have at the moment:
{% if condition %}
<a href="">
{{ content }}
</a>
{% else %}
<span>
{{ content }}
</span>
{% endif %}
I was hoping to do something such as:
{% if condition %}
<a href="">
{% include mycontent %}
</a>
{% else %}
<span>
{% include mycontent %}
</span>
{% endif %}
{% mycontent %}
{{ content }}
{% endmycontent %}
Is such a thing possible?
If you don't want to use extra files you could use macro's :
{% import _self as macro %}
{% macro foo(content) %}
{{ content }}
{% endmacro %}
{% for condition in [0, 1, 0, 1, ] %}
{% if condition %}
{{ macro.foo('Bar') }}
{% else %}
<span>{{ macro.foo('Bar') }}</span>
{% endif %}
{% endfor %}
fiddle
What you want to do has to be done using the normal syntax. an extra file. and include this file.
But if u want to do this without extra file. use the {% set variablecontent = "put content here" %} and then in your "{% mycontent %}" part u put {{ variablecontent }}
hope this helps

Navigation link works on mobile but not on desktop

i have this website http://sds-test.nowcommu.myhostpoint.ch/de (please use the "de" at the end) and the last link of the navigation "RECHENZENTRUM" does not works on desktop but works on mobile. How can i solve it? This is the twig code:
{% extends 'partials/base.html.twig' %}
{% set show_onpage_menu = header.onpage_menu == true or header.onpage_menu is null %}
{% macro pageLinkName(text) %}{{ text|lower|replace({' ':'_'}) }}{% endmacro %}
{% block javascripts %}
{% if show_onpage_menu %}
{% do assets.add('theme://js/singlePageNav.min.js') %}
{% endif %}
{{ parent() }}
{% endblock %}
{% block bottom %}
{{ parent() }}
{% if show_onpage_menu %}
<script>
// singlePageNav initialization & configuration
$('#navbar').singlePageNav({
offset: $('#header').outerHeight(),
filter: ':not(.external)',
updateHash: true,
currentClass: 'active'
});
</script>
{% endif %}
{% endblock %}
{% block header_navigation %}
{% if show_onpage_menu %}
<ul class="navigation">
{% for module in page.collection() %}
{% set current_module = (module.active or module.activeChild) ? 'active' : '' %}
<li class="{{ current_module }}">{{ module.menu }}</li>
{% endfor %}
{% set datacenter_page = page.find('/services/datacenter') %}
<li>{{ datacenter_page.menu() }}</li>
</ul>
{% else %}
{{ parent() }}
{% endif %}
{% endblock %}
{% block content %}
{{ page.content }}
{% for module in page.collection() %}
<div id="{{ _self.pageLinkName(module.menu) }}"></div>
{{ module.content }}
{% endfor %}
{% endblock %}
The 'rechenzentrum' link is rendered correctly, and copying the link location via right click gives a correct URL that opens a seemingly correct page. So the template rendering is fine.
The link has two onclick handlers attached to it, though. Probably one of them fails and thus prevents navigation. (The JS is minified so I did not try to debug it.)

Dynamic block name in TWIG

I need to add multiple blocks in my template, every with different name.
{% for item from items %}
{% block item.name %}sometext{% endblock %}
{% endfor %}
But I get error. How can I do this ?
In
Dynamic block names are not possible with Twig. There has been a discussion about it over at GitHub.
You can load blocks dynamically using the block function.
{% for item in items %}
{{ block( item.name )|raw }}
{% endfor %}
Twig documentation for the block function
If I understood the question correctly, you can do this (use parent context):
parent.html.twig
{% for item from items %}
{% set currentLoopItemName = item.name %}
{% block item_loop %}sometext{% endblock %}
{% endfor %}
override.html.twig
{% extends "base.html" %}
{% block item_loop %}
{% if item.name == 'custom' %}
// do something
{% else %}
{{ parent() }}
{% endif %}
{% endblock %}
I was attempting to do the same thing and found a solution using the template_from_string function.
_items.html.twig
{% for item in items %}
{{ '{% block ' ~ item.name ~ ' %}'}}
sometext
{{ '{% endblock %}' }}
{% endfor %}
enter code here
page.html.twig
{% embed template_from_string(include('_items.html.twig')) %}
{% block someItemName %} someDifferentText {% endblock %}
{% endembed %}
What's happening is the block tags are initially being created as text. Then we use the include function to get the rendered content of _items, as a string. Finally, we convert that string to a working template (which we can embed or extend).
This works because the template_from_string function will create and compile a template at runtime, where as normally twig is compiled before hand and unchanged at runtime.

Resources