2012-04-10 18 views
0

我試圖在每個用戶名錶的每一行上創建一個按鈕,以切換每個用戶的鎖定/解鎖功能。我想使用AJAX,所以我不必在每次重新加載頁面時都獲取所有用戶。它很容易在表中有一個AJAX動作鏈接,但是當我鎖定或解鎖用戶後,我被困在從控制器返回的內容中。作爲一種破解,我返回一個字符串,這是一個新的AJAX操作鏈接的html標記。我理論上我可以點擊動態返回的按鈕,並繼續切換鎖定/解鎖。令我驚訝的是,這實際上奏效了,直到我點擊按鈕。動態按鈕確實會返回正確的標記,但它在空白頁上。使問題更加複雜化,我使用自定義助手來輸出我的操作鏈接。我已經詳細介紹了下面的所有代碼,如果有人能夠看到可能出現的問題或更好的方式來處理這種情況,我會很感激。動態地從控制器動作返回一個AJAX動作鏈接

HTML助手:

public static string ImageActionLink(this AjaxHelper helper, string imageUrl, string altText, string actionName, object routeValues, AjaxOptions ajaxOptions) 
    { 
     var builder = new TagBuilder("img"); 
     builder.MergeAttribute("src", imageUrl); 
     builder.MergeAttribute("alt", altText); 
     var link = helper.ActionLink("[replaceme]", actionName, routeValues, ajaxOptions); 
     return link.ToHtmlString().Replace("[replaceme]", builder.ToString(TagRenderMode.SelfClosing)); 
    } 

控制器:

public string Lock(Guid id) 
    { 
     IUserMethods userMethods = new UserMethods(); 

     ISMPUser user = userMethods.GetUser(id, CompanyId); 
     string ajaxButtonHTML; 

     //For some reason breaking the button HTML into substrings and appending them together for readability causes the anchor tag to render incorrectly. 
     if (user.IsEnabled) 
     { 
      userMethods.AdministratorEnableAccount(CompanyId, CurrentUser.Id, user.Username, false); 
      ajaxButtonHTML = "<a class=\"row_selected\" href=\"/MMWeb/Admin/Lock/" + id.ToString() + "\" onclick=\"Sys.Mvc.AsyncHyperlink.handleClick(this, new Sys.UI.DomEvent(event), { insertionMode: Sys.Mvc.InsertionMode.replace, confirm: 'Lock User?', httpMethod: 'Post', updateTargetId: 'Enable-'" + user.Id + "' });\"><img src=\"/MMWeb/Content/Images/lock.png\" alt=\"Lock\"></a>"; 
     } 
     else 
     { 
      userMethods.AdministratorEnableAccount(CompanyId, CurrentUser.Id, user.Username, true); 
      ajaxButtonHTML = "<a class=\"row_selected\" href=\"/MMWeb/Admin/Lock/" + id.ToString() + "\" onclick=\"Sys.Mvc.AsyncHyperlink.handleClick(this, new Sys.UI.DomEvent(event), { insertionMode: Sys.Mvc.InsertionMode.replace, confirm: 'Lock User?', httpMethod: 'Post', updateTargetId: 'Enable-'" + user.Id + "' });\"><img src=\"/MMWeb/Content/Images/unlock.png\" alt=\"Unlock\"></a>"; 
     } 

     return ajaxButtonHTML; 
    } 

查看:

<td id="<%= Html.Encode("Enable-" + user.Id) %>" class="icon-column"> 
        <% if(user.IsEnabled) 
         { %> 
          <%--<img class="LockImg" alt="User Unlocked" src="<%= Url.Content("~/Content/Images/unlock.png") %>" />--%> 
          <%= Ajax.ImageActionLink(Url.Content("~/Content/Images/unlock.png"), "Lock", "Lock", new { id = user.Id.ToString() }, new AjaxOptions { Confirm = "Lock User?", HttpMethod = "Post", UpdateTargetId = "Enable-" + user.Id })%> 
        <% } 
         else 
         {%> 
          <%= Ajax.ImageActionLink(Url.Content("~/Content/Images/lock.png"), "Lock", "Lock", new { id = user.Id.ToString() }, new AjaxOptions { Confirm = "Unlock User?", HttpMethod = "Post", UpdateTargetId = "Enable-" + user.Id })%> 
        <% }%> 
       </td> 

回答

0

有可能有幾種方法,如:

在客戶端,當用戶點擊L時ock/Unlock鏈接,向服務器發送Ajax請求以更改鎖定狀態,並通過Ajax調用發送用戶標識;在服務器的「鎖定」操作中,更新用戶鎖定狀態並將更改的用戶狀態作爲JSON數據返回給客戶端。根據結果​​,更改鏈接的CSS以反映當前的鎖定狀態。下面是示例代碼:

查看:

<td> 
<a class='<%= (item.IsLocked ? "userLock" : "userUnlock") %>' 
    href='<%= Url.Action("ResetLock", new {id = item.Name, isLocked = item.IsLocked}) %>'> 
</a> 
</td> 

樣品CSS:

.userLock, 
.userUnlock 
{ 
    background-image: url('/MMWeb/Content/Images/lock.png'); 
    display: block; 
    height: 16px; 
    width: 16px;       
} 
.userUnlock 
{ 
    background-image: url('/MMWeb/Content/Images/unlock.png'); 
}  

JavaScript的:

<script type="text/javascript"> 
$(function() { 

    $('a.userLock, a.userUnlock').click(function (e) { 

     e.preventDefault() 
     var $this = $(this); 

     $.ajax({ 
      url: $this.attr('href'), 
      type: "POST", 
      dataType: "json", 

      success: function (result, textStatus, jqXHR) { 
       if (result.status == "Succeed") { 
        if (result.IsLocked == true) {         
         $this.removeClass('userUnlock').addClass('userLock'); 
        } 
        else {         
         $this.removeClass('userLock').addClass('userUnlock'); 
        } 
       } 
      }, 
      error: function() { 
       alert('Failed to reset lock.'); 
      } 
     }); 
    }); 
}); 
</script> 

控制器:

[HttpPost] 
    public ActionResult ResetLock(Guid id) 
    { 
     //...... 
     //Update user locking status. 
     //user.IsEnabled = !user.IsEnabled; 
     //...... 

     var updatedModel = new { 
      status = "Succeed", 
      IsLocked = user.IsEnabled 
     }; 

     return Json(updatedModel); 
    } 

這種方法可以讓您的控制器動作更加輕鬆和乾爽。 我認爲,在控制器的動作中以字符串形式生成視圖並不是一個好習慣。

另一種方法可以是:

裹在一個局部視圖(例如UserEnableView.ascx)鎖定視圖。 在更新用戶的鎖定狀態後,'鎖定'操作方法應返回部分視圖。例如

public ActionResult Lock(Guid id) 
{ 
    //...... 
    //Update user locking status. 
    //.... 
    if (Request.IsAjaxRequest()) { 
     return PartialView("UserLockView", updatedModel); 
    } 
    else{ 
     return View(updatedModel); 
    }   
} 
相關問題