1

I have a node content hierarchy of Chain (parent) and Property (child), related by an entity reference (ER) on the Property back to Chain.

Each of these node types has an ER to a Skin (custom entity) - these Skins furthermore contain ERs to Slides (another custom entity) but I don't think that's important right now (Shirley!) This is all held together with Inline Entity Form.

I have a situation that I can't work out after many attempts. There is a multi-value field on the Property create page:

  • Make a new Skin (use the IEF on this page)
  • Use the parent values (use the Chain's skin)
  • Use fallback mechanism (where Property has no value set, use the Chain value)

This means I need to either:

  • process & inject the Chain's Skin into the Property's Skin template as an additional variable, and perform the either/ors in there based on the multi-value
  • preprocess the Skin so that the correct values are already present in the template so I can just "go ahead and render" based on the multi-value.

Ideally, I'd like to be able to just use the normal {{ content }} variables in the end template, either way. The first suggestion I tried, but I have got no idea, I've tried lots of things. The second looks like it might work with some sort of hook_entity_view[_alter] or similar, but I have been unable to deduce the correct approach or find a suitable example to copy.

  • Best summary of Question I can think of: "How do I conditionally override the template values of a custom entity which is a child of a node (by ER), with the values of that node's parent node's custom entity, which is also the same entity type and also related by ER?" (up two levels, over and down!) – NikLP Apr 30 '18 at 16:23
  • Here's a gist of one of my attempts which was close but no cigar: gist.github.com/NikLP/6a8f33ed73a986fa2cac6feedba55b3c – NikLP Apr 30 '18 at 16:31
  • I may have to concede that one of my attempts, which left me with a "raw" copy of the required data (alongside the raw content entity, and its processed {{ contents }} counterpart) is the only way? Ideally, I wanted to get {{ contents }} and {{ my_other_var }} so I could use twig to do the logic (for sanity's sake) but IDK. – NikLP May 1 '18 at 10:05
  • "Use fallback mechanism (where Property has no value set, use the Chain value)" -- can you explain more? which values? – joachim May 2 '18 at 9:49
  • Added an answer with lots of codes and stuffs. Essentially, Property and Chain are little more than named (content type) containers for multiple instances of a Skin entity (linked by Entity Reference). – NikLP May 2 '18 at 10:06
0

Had to post an answer as I need to put more code.

The desired outcome is I can do this: {% if property.multivalue.value is fallback %} {% if property.somevalue is set %} {# check property for a value #} {{ content.field_image }} {# from property's skin entity #} {% else %} {{ chain.field_image }} {# FALLBACK value, from chain's skin entity #} {% end %} {% end %}

I've got as far as this in code:

function tap_preprocess_skin(&$variables) {
  // on skins where the owner node is a Property
  if (($node = \Drupal::routeMatch()->getParameter('node')) && $node instanceof \Drupal\node\NodeInterface) {
    if ($node->getType() === 'property') {

      // set a flag to decide how to handle this skin (content = inherit|fallback|new)
      $variables['skin_source'] = $node->field_property_skin_source[0]->getString();

      // additionally set a parent (chain) skin in the template
      $variables['chain_skin'] = $node->field_ref_chain[0]->entity->field_skin[0]->entity;
    }
  }
}

This gives me a scenario where I have the raw entity in the child skin template. For example, in any given node, I have {{ content }} and also there is a {{ node }}. Here, I have (for my skin), {{ content }} and {{ skin }} and {{ chain_skin }} (latterly, as per above code). However this means I have to render the fields manually, and some of the contents of the skin is more ERs and I don't really want to have to do some massive coding exercise when there's blatantly a way to make a preprocess take #skin from Chain and make let's say {{ chain_skin_content }}, rather than the raw {{ chain_skin }}.

I'd be perfectly happy at this stage to do the logic in the preprocess but I've had no luck there either. I'm sure there's some sort of entity API function that is the right point to tap into but I've not been able to deduce it.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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