<p>You're right, this isn't possible with setting <code>relatedTo</code> parameters. But you can pass your ElementCriteriaModel (with all other parameters set) to the <a href="http://buildwithcraft.com/classreference/services/ElementsService#buildElementsQuery-detail" rel="nofollow"><code>buildElementsQuery</code></a> method, to prepare a <a href="http://buildwithcraft.com/classreference/etc/db/DbCommand" rel="nofollow">DbCommand</a> object. You can now modify the query as you need (→ Craft documentation for <a href="http://buildwithcraft.com/docs/plugins/database" rel="nofollow">Database Queries</a>).</p>

<p>Use <a href="http://buildwithcraft.com/classreference/etc/db/DbCommand#join-detail" rel="nofollow"><code>join</code></a> to bring in the "matrixblocks" table and also your Matrix field's content table "matrixcontent_<em>mymatrixfield</em>". Then add the min. and max age conditions with <a href="http://buildwithcraft.com/classreference/etc/db/DbCommand#andWhere-detail" rel="nofollow"><code>andWhere</code></a>.</p>

<pre><code>private function addAgeCriteria(ElementCriteriaModel $criteria, $age)
{
    $query = craft()-&gt;elements-&gt;buildElementsQuery($criteria);

    $params = array(
        ':age' =&gt; $age
    );

    $conditions = array('and',
        'matrixcontent_mymatrixfield.field_linkedTo_minimumAge &lt;= :age',
        'matrixcontent_mymatrixfield.field_linkedTo_maximumAge &gt;= :age'
    ),

    $query-&gt;andWhere($conditions, $params);

    $query-&gt;join('matrixblocks matrixblocks', 'matrixblocks.ownerId = entries.id');
    $query-&gt;join('matrixcontent_mymatrixfield matrixcontent_mymatrixfield', 'matrixcontent_mymatrixfield.elementId = matrixblocks.id');

    $results = $query-&gt;queryAll();

    return EntryModel::populateModels($results);
}
</code></pre>

CC BY-SA 3.0
2015-06-14T14:22:20.093Z
2015-06-14T14:22:20.093Z
carlcs
<p>I've the following situation:</p>

<hr>

<h2>Accommodations (entry)</h2>

<ul>
<li>title</li>
<li>description (textfield)</li>
<li>...</li>
<li>linkedTo (matrix block)
<ul>
<li>Sport (category)</li>
<li>targetGroup (category)</li>
<li>minimumAge (number)</li>
<li>maximumAge (number)</li>
</ul></li>
</ul>

<hr>

<p>What I'm trying to do is fetch all entries (accommodations) related to a sport and targetGroup for a person of a certain age. E.g.: Entries for children with the age of 11 years in the targetGroup 'men/boys' and the sport 'football'.</p>

<p>Finding elements using <code>relatedTo</code> works for me, except I'm not able to filter the age. I'm pretty sure I'm doing something wrong here. I think it's not possible in craft to find textfield values via the relatedTo method, but the question is: How should I do this?</p>

<pre><code>private function get ()
{
    $sport      = $this-&gt;findSelectedBySlug('football');
    $targetGroup    = $this-&gt;findSelectedBySlug('men-boys');
    $age            = 11;

    $wheres = [
        "and",
        [
            'targetElement' =&gt; $sport,
            'field' =&gt; "linkedTo.sport"
        ],
        [
            'targetElement' =&gt; $targetGroup,
            'field' =&gt; "linkedTo.targetGroup"
        ],
        [
            'targetElement' =&gt; "&lt;= {$age}",
            'field' =&gt; "linkedTo.minimumAge"
        ],
        [
            'targetElement' =&gt; "&gt; {$age}",
            'field' =&gt; "linkedTo.maximumAge"
        ]
    ];

    $criteria = craft()-&gt;elements-&gt;getCriteria(ElementType::Entry);
    $criteria-&gt;section = 'accomodations';
    $criteria-&gt;relatedTo = $wheres;

    return $criteria-&gt;find();
}
private function findSelectedBySlug ($slug)
{
    $criteria = craft()-&gt;elements-&gt;getCriteria(ElementType::Category);

    $criteria-&gt;slug = $slug;

    return $criteria-&gt;first();
}   
</code></pre>

<plugin-development><matrix><relations><elementcriteriamodel>
Filtering Matrix through field value and multiple relations
# Filtering Matrix through field value and multiple relations

(Asked by: username_0 on 2015-06-02)

I've the following situation:

Accommodations (entry)

title
description (textfield)
...
linkedTo (matrix block)

Sport (category)
targetGroup (category)
minimumAge (number)
maximumAge (number)



What I'm trying to do is fetch all entries (accommodations) related to a sport and targetGroup for a person of a certain age. E.g.: Entries for children with the age of 11 years in the targetGroup 'men/boys' and the sport 'football'.
Finding elements using relatedTo works for me, except I'm not able to filter the age. I'm pretty sure I'm doing something wrong here. I think it's not possible in craft to find textfield values via the relatedTo method, but the question is: How should I do this?
private function get ()
{
    $sport      = $this->findSelectedBySlug('football');
    $targetGroup    = $this->findSelectedBySlug('men-boys');
    $age            = 11;

    $wheres = [
        "and",
        [
            'targetElement' => $sport,
            'field' => "linkedTo.sport"
        ],
        [
            'targetElement' => $targetGroup,
            'field' => "linkedTo.targetGroup"
        ],
        [
            'targetElement' => "<= {$age}",
            'field' => "linkedTo.minimumAge"
        ],
        [
            'targetElement' => "> {$age}",
            'field' => "linkedTo.maximumAge"
        ]
    ];

    $criteria = craft()->elements->getCriteria(ElementType::Entry);
    $criteria->section = 'accomodations';
    $criteria->relatedTo = $wheres;

    return $criteria->find();
}
private function findSelectedBySlug ($slug)
{
    $criteria = craft()->elements->getCriteria(ElementType::Category);

    $criteria->slug = $slug;

    return $criteria->first();
}

**Tags:** plugin-development, matrix, relations, elementcriteriamodel


---

## 1 answers

### Answer by username_1 on 2015-06-14. Score: 1 | Accepted answer

You're right, this isn't possible with setting relatedTo parameters. But you can pass your ElementCriteriaModel (with all other parameters set) to the buildElementsQuery method, to prepare a DbCommand object. You can now modify the query as you need (→ Craft documentation for Database Queries).
Use join to bring in the "matrixblocks" table and also your Matrix field's content table "matrixcontent_mymatrixfield". Then add the min. and max age conditions with andWhere.
private function addAgeCriteria(ElementCriteriaModel $criteria, $age)
{
    $query = craft()->elements->buildElementsQuery($criteria);

    $params = array(
        ':age' => $age
    );

    $conditions = array('and',
        'matrixcontent_mymatrixfield.field_linkedTo_minimumAge <= :age',
        'matrixcontent_mymatrixfield.field_linkedTo_maximumAge >= :age'
    ),

    $query->andWhere($conditions, $params);

    $query->join('matrixblocks matrixblocks', 'matrixblocks.ownerId = entries.id');
    $query->join('matrixcontent_mymatrixfield matrixcontent_mymatrixfield', 'matrixcontent_mymatrixfield.elementId = matrixblocks.id');

    $results = $query->queryAll();

    return EntryModel::populateModels($results);
}


---

