12

I have content which needs to go into a certain column so I have a field called 'column' there. I can create the array I want by hand:

{%
    set items = {
        1 : {
            0 : 'Quick Facts',
            1 : 'Agencies'
        },
        2 : {
            0 : 'Inspiration',
            1 : 'Industry Experience'
        }
    }
%}

Where 1 and 2 are the columns, and 0,1 is just a normal index. In a loop it is different. I have tried the same syntax but of course setting the variable in the loop will set the new variable every time and replace the old one. Using merge like below always gives me new keys. Is there a way to do this as easily as PHP?

{% set blocks = {} %}

{% for tab in tabs %}
    {% for key,block in tab.tabItem %}

        {% if block.type == 'about' %}
            {% set blocks = blocks|merge({ (block.column.value) : block.aboutTitle}) %}
        {% endif %}

    {% endfor %}
{% endfor %}

This is the output of the two pieces of code (first being what I want). I'd like the block.column.value to be the key.

Output

4
  • When you merge using a hash, my understanding is that it will replace (rather than append) any values that share the same hash key. So it would be impossible to do what your asking using a single loop/set statement. Can you perhaps share the loop that you are using also? Oct 26, 2014 at 14:28
  • Ok, updated with the proper data, and what I have now. You can see it's just a flat array and block.column.value isn't being used.
    – Ryan
    Oct 26, 2014 at 14:44
  • Don't know if this will help, but I tried to do something similar and found that it interpreted a number as an index instead of a key. Appending a string in front of the number fixed this. i.e. {% set blocks = blocks|merge({ ('col'~block.column.value) : block.aboutTitle }) %} Oct 26, 2014 at 16:50
  • Please note that the column is the same for some blocks, so that there might be two things in column 1.
    – Ryan
    Oct 26, 2014 at 23:54

1 Answer 1

19

You can do this using the twig attribute function:

{% set data = [
    {'column':'1','title':'Quick Facts'}, 
    {'column':'2','title':'Inspiration'}, 
    {'column':'1','title':'Agencies'}, 
    {'column':'2','title':'Industry Experience'}
] %}

{% set cols = {} %}
{% for item in data %}

    {# create a dynamic property if one doesn't exist #}
    {% if not attribute(cols, 'col' ~ item.column) is defined %}
        {% set cols = cols|merge({ ('col' ~ item.column) : [item.title] }) %}

    {# else update the dynamic property with the new title #}
    {% else %}
        {% set titles = attribute(cols, 'col' ~ item.column) %}
        {% set titles = titles|merge([item.title]) %}
        {% set cols = cols|merge({ ('col' ~ item.column) : titles }) %}

    {% endif %}
{% endfor %}

{{ dump(cols) }}

{#
array(2) { 
    ["col1"]=> array(2) {
         [0]=> string(11) "Quick Facts" 
         [1]=> string(8) "Agencies" 
    } 
    ["col2"]=> array(2) { 
        [0]=> string(11) "Inspiration" 
        [1]=> string(19) "Industry Experience" 
    } 
} 
#}
6
  • Please note that the column is the same for some blocks, so that there might be two things in column 1.
    – Ryan
    Oct 26, 2014 at 23:52
  • It never gets to the second part of the loop. Here it is with "col" i.imgur.com/zZg4AKK.png and here it is without i.imgur.com/1TKTHj1.png.
    – Ryan
    Oct 27, 2014 at 0:07
  • I see it but something is up with Twig - it just doesn't act predictably with arrays in my opinion.I changed to 'cols' but it still only shows up with 3 so it's overwriting the existing column as col1 already exists.
    – Ryan
    Oct 27, 2014 at 2:44
  • I actually created a sample data set to work with to test, and discovered the problem. In the old script 'titles' just copied the value rather then being a permanent reference to the 'cols[col1]' object property. If you set the object property again to 'titles' it will set the new titles array properly (overwriting it on each pass with the updated titles array). Oct 27, 2014 at 4:39
  • 1
    Great! Glad it's working finally (that hurt my brain). I learned through all this that the hash key issue is with php, not with twig. In php, if a hash key is defined as a number it will get redefined as an index [0,1,2,...]. Oct 27, 2014 at 5:50

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.