title: ASP.NET: How to access repeater generated elements from javascript?
body: <p>i have a series of rows that are generated using an <strong>asp:repeater</strong>:</p>
  
  <pre><code>&lt;asp:repeater ID="itemsRepeater" 
        OnItemDataBound="itemsRepeater_ItemDataBound" 
        runat="Server"&gt;
     &lt;itemtemplate&gt;
        &lt;tr&gt;
           &lt;td&gt;
              &lt;asp:HyperLink ID="linkView" runat="server"
                 Text="&lt;%# GetItemText((Item)Container.DataItem) %&gt;" 
                 NavigateUrl="&lt;%# GetViewItemUrl((Item)Container.DataItem) %&gt;" /&gt;
           &lt;/td&gt;
           &lt;td&gt;
              &lt;asp:HyperLink ID="linkDelete" runat="server"
                  Text="Delete"
                  NavigateUrl="&lt;%# GetDeleteUrl((ActionItem)Container.DataItem) %&gt;" /&gt;
           &lt;/td&gt;
        &lt;/tr&gt;
     &lt;/itemtemplate&gt;
  &lt;/asp:repeater&gt;
  </code></pre>
  
  <p>The repeater creates an HTML table, with each row containing a link to an item and (what is essentially) a "Delete" link. The above simplified example code generates HTML similar to:</p>
  
  <pre><code>&lt;TR&gt;
  &lt;TD&gt;
     &lt;A href="ViewItem.aspx?ItemGuid={19a149db-5675-4eee-835d-3d78372ca6f9}"&gt;
        AllisonAngle_SoccerGirl001.jpg
     &lt;/A&gt;
  &lt;/TD&gt;
  &lt;TD&gt;
     &lt;A href="DeleteItem.aspx?ItemGuid={19a149db-5675-4eee-835d-3d78372ca6f9}"&gt;Delete&lt;/A&gt;
  &lt;/TD&gt;
  &lt;/TR&gt;
  </code></pre>
  
  <p>Now that all works, but i want to convert the "Delete" to client side. i want to be able click the link and it will, on the client javascript:</p>
  
  <ul>
  <li>prompt an alert "Are you sure..."</li>
  <li>have javascript issue server-hit to actually delete the item they want</li>
  <li>remove the item from the client DOM tree</li>
  </ul>
  
  <p>So there are four problems to be solved:</p>
  
  <ol>
  <li>How to hook up javascript to the client-side click of the <strong>Delete</strong> link.</li>
  <li>How to know what item the user clicked <strong>Delete</strong></li>
  <li>Prevent a post-back</li>
  <li>Delete the  row that the user clicked</li>
  </ol>
  
  <p>That is my question. </p>
  
  <p>From here on you will find my rambling attempts to solve it. Don't take anything below as relating in any way to any possible accepted solution. Just because i posted code below, doesn't mean any of it is useful. And it doesn't mean i'm anywhere within spitting distance of the best solution. And because i can't make anything below work - it must have gone down the wrong road.</p>
  
  <hr>
  
  <h2>My Attempts</h2>
  
  <p><strong>Wiring Up Javascript</strong></p>
  
  <p>The first task is to convert the delete link HTML from something such as:</p>
  
  <pre><code>&lt;A href="DeleteItem.aspx?ItemGuid={19a149db-5675-4eee-835d-3d78372ca6f9}"&gt;
     Delete
  &lt;/A&gt;
  </code></pre>
  
  <p>into something more javascripty:</p>
  
  <pre><code>&lt;A href="#" 
        onclick="DeleteItem('DeleteItem.aspx?ItemGuid={19a149db-5675-4eee-835d-3d78372ca6f9}')"&gt;
     Delete
  &lt;/A&gt;
  </code></pre>
  
  <p>and the add the script:</p>
  
  <pre><code>&lt;script type="text/javascript"&gt;
     //&lt;![CDATA[
         function DeleteItem(deleteUrl)   
         {   
            //Ask the user if they really want to
            if (!confirm("Are you sure you want to delete INSERT NAME HERE?"))
            {
               return false;
            }
  
            //Call returns false if the server returned anything other than OK
            if (!DoAjaxHit(deleteUrl)
            {
               return false;
            }
  
            //Remove the table row from the browser
            var tableRow = document.getElementById("TODO-WHAT ID");
            if (row != null)
            {
               //TODO: how to delete the tableRow from the DOM tree?
               //document.Delete(tableRow) ?
            }
  
            //return false to prevent a postback
            return false;
         }
     //]]&gt;
  &lt;/script&gt;
  </code></pre>
  
  <p>What combination of ASP code can be used to create the above? i hear that <strong>asp:LinkButton</strong> has an <strong>OnClientClick</strong> event, where you can wire up a javascript function:</p>
  
  <pre><code>&lt;asp:LinkButton ID="linkDelete" runat="server"
     Text="Delete"
     OnClientClick="DeleteItem(&lt;%# GetDeleteUrl((ActionItem)Container.DataItem) %&gt;);"/&gt;
  </code></pre>
  
  <p>Problem is that the rendered HTML is literally containing:</p>
  
  <pre><code>&lt;a onclick="DeleteItem(&amp;lt;%# GetDeleteUrl((ActionItem)Container.DataItem)) %&gt;);" ...&gt;
     Delete
  &lt;/a&gt;
  </code></pre>
  
  <p>If i change the client click event handler to:</p>
  
  <pre><code>   OnClientClick="DeleteItem('todo - figure this out');"/&gt;
  </code></pre>
  
  <p>it works - as well as "todo - figure this out" can work.</p>
  
  <hr>
  
  <p><strong>Preventing Postbacks</strong></p>
  
  <p>The dummied down above javascript call actually happens (i can see my alert), but there's the next problem: Returning false from the javascript function doesn't prevent a postback. In fact, i can see that the <em>href</em> on the generated html code isn't "#", but rather</p>
  
  <pre><code>javascript:__doPostBack('ctl0....
  </code></pre>
  
  <p>i tried changing the ASPX code to include the OnClick handler myself:</p>
  
  <pre><code>   OnClick="#"
     OnClientClick="DeleteItem('todo - figure this out');"
  </code></pre>
  
  <p>But the compiler thinks the pound side is a pragma, and whines:</p>
  
  <blockquote>
    <p>Preprocessor directives must appear as
    the first non-whitespace character on
    a line</p>
  </blockquote>
  
  <hr>
  
  <p><strong>Table Row Identity</strong></p>
  
  <p>The table rows don't have an ID, they're generated by the <strong>asp:repeater</strong>.</p>
  
  <p>How can the javascript function know what  triggered the click event? The javascript needs to be able to find the  element, and remove it from the tree. </p>
  
  <p><strong>Note:</strong> i would of course prefer fade+collapse animation. </p>
  
  <p>Normally you get an element by using</p>
  
  <pre><code>var tr = document.getElementById("the table row's id");
  </code></pre>
  
  <p>But the table rows don't have an easily knowable ID. Since there are multiple rows, the server generates the ID as it builds the table. i realize some solution is going to have to involve changing:</p>
  
  <pre><code>&lt;TR&gt;
  </code></pre>
  
  <p>into</p>
  
  <pre><code>&lt;TR runat="server"&gt;
  </code></pre>
  
  <p>so that there will be server generated identity for each table row, but how do i reference the generated name from javsscript? </p>
  
  <p>Normally i would have thought that the scripting problem would be solved by using multiple paramters:</p>
  
  <pre><code>function DeleteItem(tableRowElement, deleteUrl)
  {
     //Do a web-hit of deleteUrl to delete the item
  
  
     //remove tableRowElement DOM object from the document tree
  }
  </code></pre>
  
  <p>But the problem is just pushed elsewhere: How do you populate tableRowElement and deleteUrl for the call to the javascript function?</p>
  
  <hr>
  
  <p>Such a simple problem: convert a click from a postback to client-side.</p>
  
  <p>The volume of problems involved is getting quite idiotic. Which seems to indicate that either</p>
  
  <ul>
  <li>the idea solution is something completely different</li>
  <li>there is no solution</li>
  </ul>
  
  <hr>
  
  <h2>References</h2>
  
  <p><a href="https://stackoverflow.com/questions/183179/how-do-i-fade-a-row-out-before-postback">Stackoverflow: How do I fade a row out before postback?</a></p>
  
  <p><a href="https://stackoverflow.com/questions/218733/javascript-before-aspbuttonfield-click">Stackoverflow: Javascript before asp:ButtonField click</a></p>
  
  <p><a href="http://forums.asp.net/p/1116342/1733360.aspx" rel="nofollow noreferrer">asp.net: Accessing repeater elements from javascript.</a></p>
  
  <p><a href="https://stackoverflow.com/questions/480195/asp-net-how-to-access-repeater-generated-elements">Stackoverflow: How to access repeater generated elements?</a></p>