วิธีที่ดีที่สุดในการแทนที่ลิงก์ด้วยรูปภาพโดยใช้ Razor ใน MVC3 คืออะไร ฉันเพิ่งทำสิ่งนี้ในขณะนี้:
<a href="@Url.Action("Edit", new { id=MyId })"><img src="../../Content/Images/Image.bmp", alt="Edit" /></a>
มีวิธีที่ดีกว่า?
วิธีที่ดีที่สุดในการแทนที่ลิงก์ด้วยรูปภาพโดยใช้ Razor ใน MVC3 คืออะไร ฉันเพิ่งทำสิ่งนี้ในขณะนี้:
<a href="@Url.Action("Edit", new { id=MyId })"><img src="../../Content/Images/Image.bmp", alt="Edit" /></a>
มีวิธีที่ดีกว่า?
คำตอบ:
คุณสามารถสร้างวิธีการขยายสำหรับ HtmlHelper เพื่อลดความซับซ้อนของโค้ดในไฟล์ CSHTML ของคุณ คุณสามารถแทนที่แท็กของคุณด้วยวิธีการดังนี้:
// Sample usage in CSHTML
@Html.ActionImage("Edit", new { id = MyId }, "~/Content/Images/Image.bmp", "Edit")
นี่คือตัวอย่างวิธีการขยายสำหรับโค้ดด้านบน:
// Extension method
public static MvcHtmlString ActionImage(this HtmlHelper html, string action, object routeValues, string imagePath, string alt)
{
var url = new UrlHelper(html.ViewContext.RequestContext);
// build the <img> tag
var imgBuilder = new TagBuilder("img");
imgBuilder.MergeAttribute("src", url.Content(imagePath));
imgBuilder.MergeAttribute("alt", alt);
string imgHtml = imgBuilder.ToString(TagRenderMode.SelfClosing);
// build the <a> tag
var anchorBuilder = new TagBuilder("a");
anchorBuilder.MergeAttribute("href", url.Action(action, routeValues));
anchorBuilder.InnerHtml = imgHtml; // include the <img> tag inside
string anchorHtml = anchorBuilder.ToString(TagRenderMode.Normal);
return MvcHtmlString.Create(anchorHtml);
}
routeValues
เป็นActionResult
จากนั้นในurl.Action
ฟังก์ชั่นเปลี่ยนrouteValues
เป็นrouteValues.GetRouteValueDictionary()
/configuration/system.web/pages/namespaces
องค์ประกอบ
alt
ยอมรับฉันยอมรับวัตถุเพื่อรับคุณสมบัติ html โดยใช้วัตถุที่ไม่ระบุตัวตนvar attributes = HtmlHelper.AnonymousObjectToHtmlAttributes(htmlAttributes);
ในที่สุดforeach (var attr in attributes){ imgBuilder.MergeAttribute(attr.Key, attr.Value.ToString());}
/Views
โฟลเดอร์ระดับบนสุด
คุณสามารถใช้Url.Content
สิ่งที่ใช้ได้กับลิงก์ทั้งหมดเนื่องจากแปลเครื่องหมายทิลเดอ~
เป็นรูท uri
<a href="@Url.Action("Edit", new { id=MyId })">
<img src="@Url.Content("~/Content/Images/Image.bmp")", alt="Edit" />
</a>
<a href="@Url.Action("Index","Home")"><img src="@Url.Content("~/Content/images/myimage.gif")" alt="Home" /></a>
จากคำตอบของ Lucas ข้างต้นนี่คือโอเวอร์โหลดที่ใช้ชื่อคอนโทรลเลอร์เป็นพารามิเตอร์คล้ายกับ ActionLink ใช้โอเวอร์โหลดนี้เมื่อรูปภาพของคุณเชื่อมโยงกับการดำเนินการในคอนโทรลเลอร์อื่น
// Extension method
public static MvcHtmlString ActionImage(this HtmlHelper html, string action, string controllerName, object routeValues, string imagePath, string alt)
{
var url = new UrlHelper(html.ViewContext.RequestContext);
// build the <img> tag
var imgBuilder = new TagBuilder("img");
imgBuilder.MergeAttribute("src", url.Content(imagePath));
imgBuilder.MergeAttribute("alt", alt);
string imgHtml = imgBuilder.ToString(TagRenderMode.SelfClosing);
// build the <a> tag
var anchorBuilder = new TagBuilder("a");
anchorBuilder.MergeAttribute("href", url.Action(action, controllerName, routeValues));
anchorBuilder.InnerHtml = imgHtml; // include the <img> tag inside
string anchorHtml = anchorBuilder.ToString(TagRenderMode.Normal);
return MvcHtmlString.Create(anchorHtml);
}
คุณสามารถใช้โซลูชัน @Lucas ได้ แต่ก็มีวิธีอื่นเช่นกัน
@Html.ActionLink("Update", "Update", *Your object value*, new { @class = "imgLink"})
ตอนนี้เพิ่มคลาสนี้ในไฟล์ CSS หรือในเพจของคุณ:
.imgLink
{
background: url(YourImage.png) no-repeat;
}
ด้วยคลาสนั้นลิงก์ใด ๆ ก็จะมีรูปภาพที่คุณต้องการ
ControllerName
ลงมือทำ ดังนี้@Html.ActionLink("Update", "Update", "*Your Controller*",*object values*, new {@class = "imgLink"})
สิ่งนี้กลายเป็นกระทู้ที่มีประโยชน์มาก
สำหรับผู้ที่แพ้เครื่องมือจัดฟันแบบลอนนี่คือคำตอบของ Lucas 'และ Crake เวอร์ชัน VB.NET:
Public Module ActionImage
<System.Runtime.CompilerServices.Extension()>
Function ActionImage(html As HtmlHelper, Action As String, RouteValues As Object, ImagePath As String, AltText As String) As MvcHtmlString
Dim url = New UrlHelper(html.ViewContext.RequestContext)
Dim imgHtml As String
'Build the <img> tag
Dim imgBuilder = New TagBuilder("img")
With imgBuilder
.MergeAttribute("src", url.Content(ImagePath))
.MergeAttribute("alt", AltText)
imgHtml = .ToString(TagRenderMode.Normal)
End With
Dim aHtml As String
'Build the <a> tag
Dim aBuilder = New TagBuilder("a")
With aBuilder
.MergeAttribute("href", url.Action(Action, RouteValues))
.InnerHtml = imgHtml 'Include the <img> tag inside
aHtml = aBuilder.ToString(TagRenderMode.Normal)
End With
Return MvcHtmlString.Create(aHtml)
End Function
<Extension()>
Function ActionImage(html As HtmlHelper, Action As String, Controller As String, RouteValues As Object, ImagePath As String, AltText As String) As MvcHtmlString
Dim url = New UrlHelper(html.ViewContext.RequestContext)
Dim imgHtml As String
'Build the <img> tag
Dim imgBuilder = New TagBuilder("img")
With imgBuilder
.MergeAttribute("src", url.Content(ImagePath))
.MergeAttribute("alt", AltText)
imgHtml = .ToString(TagRenderMode.Normal)
End With
Dim aHtml As String
'Build the <a> tag
Dim aBuilder = New TagBuilder("a")
With aBuilder
.MergeAttribute("href", url.Action(Action, Controller, RouteValues))
.InnerHtml = imgHtml 'Include the <img> tag inside
aHtml = aBuilder.ToString(TagRenderMode.Normal)
End With
Return MvcHtmlString.Create(aHtml)
End Function
End Module
วิธีการขยายนี้ใช้งานได้เช่นกัน (วางไว้ในคลาสคงที่สาธารณะ):
public static MvcHtmlString 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 new MvcHtmlString( link.ToHtmlString().Replace("[replaceme]", builder.ToString(TagRenderMode.SelfClosing)) );
}
หากต้องการเพิ่มให้กับงาน Awesome ทั้งหมดที่เริ่มโดยลุคฉันกำลังโพสต์อีกหนึ่งงานที่ใช้ค่าคลาส css และถือว่าคลาสและ alt เป็นพารามิเตอร์เสริม (ใช้ได้ภายใต้ ASP.NET 3.5+) วิธีนี้จะช่วยให้สามารถใช้งานได้มากขึ้น แต่ลดจำนวนวิธีการที่มากเกินไปที่จำเป็น
// Extension method
public static MvcHtmlString ActionImage(this HtmlHelper html, string action,
string controllerName, object routeValues, string imagePath, string alt = null, string cssClass = null)
{
var url = new UrlHelper(html.ViewContext.RequestContext);
// build the <img> tag
var imgBuilder = new TagBuilder("img");
imgBuilder.MergeAttribute("src", url.Content(imagePath));
if(alt != null)
imgBuilder.MergeAttribute("alt", alt);
if (cssClass != null)
imgBuilder.MergeAttribute("class", cssClass);
string imgHtml = imgBuilder.ToString(TagRenderMode.SelfClosing);
// build the <a> tag
var anchorBuilder = new TagBuilder("a");
anchorBuilder.MergeAttribute("href", url.Action(action, controllerName, routeValues));
anchorBuilder.InnerHtml = imgHtml; // include the <img> tag inside
string anchorHtml = anchorBuilder.ToString(TagRenderMode.Normal);
return MvcHtmlString.Create(anchorHtml);
}
การปรับเปลี่ยนสไลด์เปลี่ยน Helper
public static IHtmlString ActionImageLink(this HtmlHelper html, string action, object routeValues, string styleClass, string alt)
{
var url = new UrlHelper(html.ViewContext.RequestContext);
var anchorBuilder = new TagBuilder("a");
anchorBuilder.MergeAttribute("href", url.Action(action, routeValues));
anchorBuilder.AddCssClass(styleClass);
string anchorHtml = anchorBuilder.ToString(TagRenderMode.Normal);
return new HtmlString(anchorHtml);
}
CSS คลาส
.Edit {
background: url('../images/edit.png') no-repeat right;
display: inline-block;
height: 16px;
width: 16px;
}
สร้างลิงค์เพียงแค่ส่งชื่อคลาส
@Html.ActionImageLink("Edit", new { id = item.ID }, "Edit" , "Edit")
ฉันได้เข้าร่วมคำตอบจาก Lucas และ " ASP.NET MVC Helpers การรวมวัตถุ htmlAttributes สองตัวเข้าด้วยกัน " และบวก controllerName เข้ากับรหัสต่อไปนี้:
// ตัวอย่างการใช้งานใน CSHTML
@Html.ActionImage("Edit",
"EditController"
new { id = MyId },
"~/Content/Images/Image.bmp",
new { width=108, height=129, alt="Edit" })
และคลาสส่วนขยายสำหรับโค้ดด้านบน:
using System.Collections.Generic;
using System.Reflection;
using System.Web.Mvc;
namespace MVC.Extensions
{
public static class MvcHtmlStringExt
{
// Extension method
public static MvcHtmlString ActionImage(
this HtmlHelper html,
string action,
string controllerName,
object routeValues,
string imagePath,
object htmlAttributes)
{
///programming/4896439/action-image-mvc3-razor
var url = new UrlHelper(html.ViewContext.RequestContext);
// build the <img> tag
var imgBuilder = new TagBuilder("img");
imgBuilder.MergeAttribute("src", url.Content(imagePath));
var dictAttributes = htmlAttributes.ToDictionary();
if (dictAttributes != null)
{
foreach (var attribute in dictAttributes)
{
imgBuilder.MergeAttribute(attribute.Key, attribute.Value.ToString(), true);
}
}
string imgHtml = imgBuilder.ToString(TagRenderMode.SelfClosing);
// build the <a> tag
var anchorBuilder = new TagBuilder("a");
anchorBuilder.MergeAttribute("href", url.Action(action, controllerName, routeValues));
anchorBuilder.InnerHtml = imgHtml; // include the <img> tag inside
string anchorHtml = anchorBuilder.ToString(TagRenderMode.Normal);
return MvcHtmlString.Create(anchorHtml);
}
public static IDictionary<string, object> ToDictionary(this object data)
{
///programming/6038255/asp-net-mvc-helpers-merging-two-object-htmlattributes-together
if (data == null) return null; // Or throw an ArgumentNullException if you want
BindingFlags publicAttributes = BindingFlags.Public | BindingFlags.Instance;
Dictionary<string, object> dictionary = new Dictionary<string, object>();
foreach (PropertyInfo property in
data.GetType().GetProperties(publicAttributes))
{
if (property.CanRead)
{
dictionary.Add(property.Name, property.GetValue(data, null));
}
}
return dictionary;
}
}
}
นี่จะเป็นการทำงานที่ดีมาก
<a href="<%:Url.Action("Edit","Account",new { id=item.UserId }) %>"><img src="../../Content/ThemeNew/images/edit_notes_delete11.png" alt="Edit" width="25px" height="25px" /></a>
~/Content
) เส้นทางที่../../Content
อาจจะไม่ถูกต้องจากเส้นทางที่แตกต่างกัน (เช่น/
,/Home
,/Home/Index
)