Copied to clipboard

Flag this post as spam?

This post will be reported to the moderators as potential spam to be looked at


  • apload-gmbh 39 posts 109 karma points
    Nov 17, 2023 @ 13:53
    apload-gmbh
    0

    Get a list of used Perplex elements

    Usually we just let render the content of the Perplex elements, but now we would like to use them as an anchor sub navigation on a onepager.

    We use Umbraco 9.5.0 with Perplex.ContentBlocks 2.1.5

    Can anyone give us a hint, how or where we get a start to find a solution.

    Thanks all

  • Daniël Knippers 153 posts 1116 karma points MVP 2x c-trib
    Nov 17, 2023 @ 14:10
    Daniël Knippers
    0

    Hi,

    I wonder what you are looking for? It seems you already have everything you need.

    1. List of blocks on a page -> Model.Content.ContentBlocks.Header + Model.Content.ContentBlocks.Blocks (this assumes you use ModelsBuilder and the property alias is "contentBlocks").
      Without ModelsBuilder you can use: IPublishedContent content = ...; var contentBlocks = content.Value<IContentBlocks>("contentBlocks").

    2. You probably want to add some unique id to each content block you render, so you can use JavaScript to navigate to it. For example, in your partial views that you use for the content blocks you can just add something like this:

      @inherits UmbracoViewPage<IContentBlockViewModel<...>>
      <div data-block-id="@Model.Id">
          ... block content here
      </div>
      

    And then use JS to scroll the window to the top of the content block div when you click on your navigation list.

    Hope this helps.

  • apload-gmbh 39 posts 109 karma points
    Nov 17, 2023 @ 16:06
    apload-gmbh
    0

    Hi Daniël

    Thanks a lot for your quick reply, and sorry for my unclear problem description.

    Your answer 2 helps me already a little bit, but I am unsure if i know everything I will need.

    What I like to achieve is something without JavaScript:

    <nav>
    <ul>
      <li>Home</li>
      <li>About us
        <ul>
          <li><a href="/about-us/#blockName1">PerplexBlock 1</a></li>
          <li><a href="/about-us/#blockName2">PerplexBlock 2</a></li>
          <li><a href="/about-us/#blockName3">PerplexBlock 3</a></li>
        <ul>
      </li>
      <li>Contact</li>
    </ul>
    </nav>
    
  • apload-gmbh 39 posts 109 karma points
    Nov 17, 2023 @ 16:15
    apload-gmbh
    0

    And in the body

    <main>
      <section id="blockName1"></section>
      <section id="blockName2"></section>
      <section id="blockName3"></section>
    </main>
    
  • Daniël Knippers 153 posts 1116 karma points MVP 2x c-trib
    Nov 20, 2023 @ 07:50
    Daniël Knippers
    0

    Each ContentBlock can just render the <section id="..."> right (in their partial view)? So that's that. Then the only thing you need to do is somehow render that <ul> in your _Layout file, right? In your Layout you can just read the ContentBlocks of the current page using @Model.Content.Value<IContentBlocks>("contentBlocks"), so I am not sure what other information you are looking for?

  • apload-gmbh 39 posts 109 karma points
    Nov 29, 2023 @ 18:19
    apload-gmbh
    0

    Thanks Daniël

    Your guessing right. I tried something like the following:

    <ul class="navbar">
      <li>
        <a href="#>MainNavName</a>
        @{
             var perplexBlocks = item.Value<IContentBlocks>("contentBlocks");
             if (perplexBlocks.Any()) {
                  <ul class="navbar>
                    foreach(var ppItem in perplexBlocks)
                    {
                      <li class="subAnchor">
                        <a href="#anchor1>AnchorName</a>
                      </li>
                    }
                  </ul>
              }
           }
          </li>
        </ul>
    

    But it doesn't work because IContentBlocks has no GetEnumerator. I tried also

    var perplexBlocks = item.Value<IEnumerable<IContentBlocks>>("contentBlocks");
    

    and

    var perplexBlocks = item.ContentBlocks;
    

    but I am stucked.

    Is there a special using directive?

    I use

    @inherits Umbraco.Cms.Web.Common.Views.UmbracoViewPage
    @using Umbraco.Cms.Web.Common.PublishedModels;
    @using Umbraco9.Core.Perplex_ContentBlocks;
    @using Umbraco.Cms.Core.Models.PublishedContent;
    

    Kind regards

    Jan

  • Daniël Knippers 153 posts 1116 karma points MVP 2x c-trib
    Nov 30, 2023 @ 08:27
    Daniël Knippers
    1

    Hi Jan,

    If you debug using Visual Studio you can inspect the variables that would make your life much easier I think.

    Anyway, IContentBlocks is not an Enumerable. It has a .Header property for the Header ContentBlock and a .Blocks which IS an IEnumerable of all IContentBlockViewModels. So instead of perplexBlocks.Any() try perplexBlocks.Blocks.Any(). Just keep in mind this does not include the Header block (which is perplexBlocks.Header).

  • apload-gmbh 39 posts 109 karma points
    Nov 30, 2023 @ 14:28
    apload-gmbh
    0

    Thanks a lot Daniël

    .Block was the thing I was looking for.

    My slightly simplified solution for the submenu in the navbar looks like:

    @if (children2ndLevel)
            {
            <ul>
                  var perplexBlocks_init = item.Value<IContentBlocks>("contentBlocks");
                    @foreach (var block in perplexBlocks_init.Blocks)
                    {
                        if (block.Content != null)
                        {
                        <li>
                     @{
                         string elBlock = block.Content.ToString();
                         string anchorName, anchorNomalized;
    
                          <a href="#@(Regex.Replace(anchorNomalized, @"[^\u0000-\u007F]", string.Empty))">
                              @anchorName
                          </a>
                         }
    
                    </li>
                  }
                }
        </ul>
    

    I hope this may also help other coders.

Please Sign in or register to post replies

Write your reply to:

Draft