skip to Main Content

I am iterating through a LARGE list of objects all of which will open the same modal window that will be loaded with dynamic information. To make this work, I create a counter called MenuCounter that I know increments just fine.

That said, I am attempting to wrap a hyperlink around the icons I need to use and the injection of the method keeps pointing to the last value of the MenuCounter.

I first tried this:

<a href="#" onclick="@(() => SetupChangeName(MenuCounter))" class="menuButton">...</a>

When I ran into the issue, I tried reducing the code to the following but then the page somehow activates the hyperlink and the modal window appears and will not go away.

<a href="#" onclick="SetupChangeName(MenuCounter)" class="menuButton">...</a>

Can somebody please help me out?

Thank you!

2

Answers


  1. I’m not a fan of onclick attributes, but if you’re set on this method, I believe you just need to santize the C# and JS in the same line like this:

    <a href="#" onclick="SetupChangeName('@MenuCounter')" class="menuButton">...</a>
    

    Adding the quotes will ensure at least an empty string is present for JS, and then you can process it.

    Alternative method

    Since mixing languages like that is quite frustrating, I find it easier to use data tags, for example

    <a href="#" data-menu-counter="@MenuCounter" class="menuButton">...</a>
    

    And then in your JS file:

    var links = document.querySelectorAll('[data-menu-counter]');
    links.forEach(x => x.addEventListener('click', /* your function code here */);
    
    Login or Signup to reply.
  2. You should apply a lambda expression to the Blazor @onclick directive instead of using the onclick Html attribute, in which case it should call a JS function, which you did not mean.

    Note that I’ve introduced a new directive to prevent the default action of the anchor element: @onclick:preventDefault

    Test this code:

    @page "/"
    
    
    <a href="#" @onclick:preventDefault @onclick="@(() => SetupChangeName(MenuCounter))" >Click me...</a>
    
     <div>Counter is @output</div>
    @code
    {
        private int MenuCounter = 10;
        private int output;
    
        private void SetupChangeName (int counter)
        {
            output = counter;
        }
    }
    

    Note: If you use a for loop to render a list of anchor elements, you must define a variable local to the loop, and provide it as the input to your lambda expression, something like this:

    @for(int MenuCounter = 0; MenuCounter < 10; MenuCounter++)
    {
       int local= MenuCounter; 
       <a href="#" @onclick:preventDefault @onclick="@(() => 
           SetupChangeName(local))" >Click me...</a> 
    }
    

    otherwise, all the lambda expressions will have the the same value for MenuCounter, which is the value incremented for the last iteration. See For loop not returning expected value – C# – Blazor explaining the issue.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search