วาง HTML ไว้ใน Html.ActionLink () และไม่ต้องเชื่อมโยงข้อความ?


169

ฉันมีสองคำถาม:

  1. ฉันสงสัยว่าฉันจะไม่แสดงข้อความลิงก์ได้อย่างไรเมื่อใช้Html.ActionLink()ในมุมมอง MVC (อันที่จริงนี่คือSite.Master)

ไม่มีรุ่นที่โอเวอร์โหลดที่ไม่อนุญาตให้มีข้อความลิงค์และเมื่อฉันลองส่งเป็นช่องว่างstringคอมไพเลอร์บอกฉันว่ามันต้องการสตริงที่ไม่ว่างเปล่า

ฉันจะแก้ไขสิ่งนี้ได้อย่างไร

  1. ฉันต้องวาง<span>แท็กไว้ในแท็กจุดยึด แต่ไม่สามารถใช้งานHtml.ActionLink();ได้ ฉันต้องการที่จะเห็นผลลัพธ์ต่อไปนี้:

    ขยายข้อความ

ฉันจะวางแท็กไว้ในที่ยึดแท็กใน ASP.NET MVC ได้อย่างไร


อะไรคือวัตถุประสงค์ / การใช้ลิงก์การกระทำที่ว่างเปล่า?
David

1
ฉันใช้เทพดารูปภาพสำหรับแถบการนำทางและสิ่งที่<li>คุณเห็นคือปุ่มการนำทางเฉพาะ (พร้อมขนาด POS พื้นหลัง ฯลฯ ที่ระบุใน css stylesheet) แต่มันจะต้องเชื่อมโยงกับบางสิ่งดังนั้นฉันไม่ต้องการแสดงข้อความ ฉันต้องการเทพดาที่จะทำเพื่อฉัน
MegaMatt

คำตอบ:


322

แทนที่จะใช้ Html.ActionLink คุณสามารถแสดง URL ผ่าน Url.Action

<a href="<%= Url.Action("Index", "Home") %>"><span>Text</span></a>
<a href="@Url.Action("Index", "Home")"><span>Text</span></a>

และในการทำ URL ว่างให้คุณทำได้

<a href="<%= Url.Action("Index", "Home") %>"></a>
<a href="@Url.Action("Index", "Home")"></a>

3
ฉันต้องใช้ <a สิ่งนี้ แต่อาจเป็นประโยชน์สำหรับผู้ที่ต้องการใช้คำตอบข้างต้นและพบว่ามันไม่ได้ผล
Dave Haigh

2
@ Url.Action เมื่อใช้เทมเพลตมีดโกน ฉันได้อัปเดตคำตอบแล้วเพื่อให้คุณเห็นทั้งคู่
David

<a href=@Url.Action("Create", "Product")><span>Create</span></a>ยังใช้งานได้ ไม่จำเป็นต้องใส่เครื่องหมายคำพูด
เดวิด

1
สำหรับเนื้อหาแบบคงที่ทำไมไม่พิมพ์ html โดยตรง ดูเหมือนว่า verbose น้อยลงและเรียบง่ายขึ้น
SkeetJon

ไม่ใช่ตัวเลือกจริงใน Asp.Net Core 2 อีกต่อไปหากคุณต้องการใช้ Ajax
Zorkind

17

ส่วนขยาย HtmlHelper ที่กำหนดเองเป็นอีกตัวเลือกหนึ่ง หมายเหตุ : ParameterDictionary เป็นประเภทของฉันเอง คุณสามารถทดแทน RouteValueDictionary แต่คุณจะต้องสร้างมันให้แตกต่างออกไป

public static string ActionLinkSpan( this HtmlHelper helper, string linkText, string actionName, string controllerName, object htmlAttributes )
{
    TagBuilder spanBuilder = new TagBuilder( "span" );
    spanBuilder.InnerHtml = linkText;

    return BuildNestedAnchor( spanBuilder.ToString(), string.Format( "/{0}/{1}", controllerName, actionName ), htmlAttributes );
}

private static string BuildNestedAnchor( string innerHtml, string url, object htmlAttributes )
{
    TagBuilder anchorBuilder = new TagBuilder( "a" );
    anchorBuilder.Attributes.Add( "href", url );
    anchorBuilder.MergeAttributes( new ParameterDictionary( htmlAttributes ) );
    anchorBuilder.InnerHtml = innerHtml;

    return anchorBuilder.ToString();
}

14

นี่คือวิธีแก้ปัญหา (ต่ำและสกปรก) ในกรณีที่คุณต้องการใช้ ajax หรือคุณสมบัติบางอย่างที่คุณไม่สามารถใช้เมื่อสร้างลิงก์ด้วยตนเอง (โดยใช้แท็ก):

<%= Html.ActionLink("LinkTextToken", "ActionName", "ControllerName").ToHtmlString().Replace("LinkTextToken", "Refresh <span class='large sprite refresh'></span>")%>

คุณสามารถใช้ข้อความใด ๆ แทน 'LinkTextToken' ซึ่งจะมีการแทนที่เท่านั้นมันเป็นสิ่งสำคัญเท่านั้นที่จะไม่เกิดขึ้นที่ใด ๆ ภายใน actionlink


6
+1 ความคิดที่ดี ในมีดโกนคุณจะต้องแร็พทั้งหมดในHtml.Raw()
Carrie Kendall

ขอบคุณ :) ตอนนี้ฉันเห็นสิ่งที่เราใช้แล้วฉันเกือบจะเขินอายการทำสิ่งเหล่านี้บนเซิร์ฟเวอร์ก็เป็นการสิ้นเปลืองทรัพยากรของเซิร์ฟเวอร์ ...
Goran Obradovic

1
ขณะที่ฉันใช้ @ Ajax.ActionLink และไม่รู้สึกอยากตั้งค่าdate-คุณลักษณะทั้งหมดด้วยตนเองนี่เป็นทางออกที่ดีที่สุดสำหรับฉัน +1
asontu

ขอบคุณทำงานเหมือนจับใจเมื่อฉันยังใช้ Ajax.ActionLink ดูเหมือนว่ามันจะไม่ทำให้อะไรช้าลงและฉันก็ต้องรักษาเลย์เอาต์และสไตล์ไว้เหมือนเดิม
Blacky Wolf

แค่อยากบอกว่านี่ไม่ได้ผลใน. Net Core, ToHtmlString () ถูกลบใน v2 แล้วไม่แน่ใจเกี่ยวกับ v1
Zorkind

12

เพียงใช้Url.ActionแทนHtml.ActionLink:

<li id="home_nav"><a href="<%= Url.Action("ActionName") %>"><span>Span text</span></a></li>

@CraigStunz ทำไมเราควรใช้ Url.Action แทน Html.ActionLink
Roxy'Pro

6

มันใช้ได้ดีสำหรับฉันเสมอ มันไม่ยุ่งและสะอาดมาก

<a href="@Url.Action("Index", "Home")"><span>Text</span></a>


Url.Action ไม่มีตัวสร้างที่จะใช้ htmlAttributes ไม่เหมือน ActionLink
barrypicker

2

ฉันสิ้นสุดด้วยวิธีส่วนขยายที่กำหนดเอง มันน่าสังเกตว่าเมื่อพยายามวาง HTML ไว้ในวัตถุ Anchor ข้อความลิงค์สามารถเป็นได้ทั้งทางซ้ายหรือทางขวาของ HTML ภายใน ด้วยเหตุนี้ฉันเลือกที่จะให้พารามิเตอร์สำหรับ HTML ภายในและด้านซ้าย - ข้อความลิงค์อยู่ตรงกลาง HTML ภายในทั้งด้านซ้ายและขวาเป็นทางเลือก

ส่วนขยายวิธีการ ActionLinkInnerHtml:

    public static MvcHtmlString ActionLinkInnerHtml(this HtmlHelper helper, string linkText, string actionName, string controllerName, RouteValueDictionary routeValues = null, IDictionary<string, object> htmlAttributes = null, string leftInnerHtml = null, string rightInnerHtml = null)
    {
        // CONSTRUCT THE URL
        var urlHelper = new UrlHelper(helper.ViewContext.RequestContext);
        var url = urlHelper.Action(actionName: actionName, controllerName: controllerName, routeValues: routeValues);

        // CREATE AN ANCHOR TAG BUILDER
        var builder = new TagBuilder("a");
        builder.InnerHtml = string.Format("{0}{1}{2}", leftInnerHtml, linkText, rightInnerHtml);
        builder.MergeAttribute(key: "href", value: url);

        // ADD HTML ATTRIBUTES
        builder.MergeAttributes(htmlAttributes, replaceExisting: true);

        // BUILD THE STRING AND RETURN IT
        var mvcHtmlString = MvcHtmlString.Create(builder.ToString());
        return mvcHtmlString;
    }

ตัวอย่างการใช้งาน:

นี่คือตัวอย่างของการใช้งาน สำหรับตัวอย่างนี้ฉันต้องการเพียงแค่ html ด้านในทางด้านขวาของข้อความลิงก์ ...

@Html.ActionLinkInnerHtml(
    linkText: "Hello World"
        , actionName: "SomethingOtherThanIndex"
        , controllerName: "SomethingOtherThanHome"
        , rightInnerHtml: "<span class=\"caret\" />"
        )

ผล:

ผลลัพธ์นี้ใน HTML ต่อไปนี้ ...

<a href="/SomethingOtherThanHome/SomethingOtherThanIndex">Hello World<span class="caret" /></a>

1

ฉันคิดว่านี่อาจเป็นประโยชน์เมื่อใช้ bootstrap และ glypicons บางอย่าง:

<a class="btn btn-primary" 
    href="<%: Url.Action("Download File", "Download", 
    new { id = msg.Id, distributorId = msg.DistributorId }) %>">
    Download
    <span class="glyphicon glyphicon-paperclip"></span>
</a>

สิ่งนี้จะแสดงแท็ก A พร้อมลิงค์ไปยังคอนโทรลเลอร์พร้อมไอคอนคลิปหนีบกระดาษที่ดีเพื่อแสดงลิงค์ดาวน์โหลดและเอาต์พุต html นั้นสะอาด


1

นี่คือการขยายคำตอบของ @ tvanfosson uber ฉันได้แรงบันดาลใจจากมันและตัดสินใจที่จะทำให้มันเป็นเรื่องธรรมดามากขึ้น

    public static MvcHtmlString NestedActionLink(this HtmlHelper htmlHelper, string linkText, string actionName,
        string controllerName, object routeValues = null, object htmlAttributes = null,
        RouteValueDictionary childElements = null)
    {
        var htmlAttributesDictionary = HtmlHelper.AnonymousObjectToHtmlAttributes(htmlAttributes);

        if (childElements != null)
        {
            var urlHelper = new UrlHelper(htmlHelper.ViewContext.RequestContext);

            var anchorTag = new TagBuilder("a");
            anchorTag.MergeAttribute("href",
                routeValues == null
                    ? urlHelper.Action(actionName, controllerName)
                    : urlHelper.Action(actionName, controllerName, routeValues));
            anchorTag.MergeAttributes(htmlAttributesDictionary);
            TagBuilder childTag = null;

            if (childElements != null)
            {
                foreach (var childElement in childElements)
                {
                    childTag = new TagBuilder(childElement.Key.Split('|')[0]);
                    object elementAttributes;
                    childElements.TryGetValue(childElement.Key, out elementAttributes);

                    var attributes = HtmlHelper.AnonymousObjectToHtmlAttributes(elementAttributes);

                    foreach (var attribute in attributes)
                    {
                        switch (attribute.Key)
                        {
                            case "@class":
                                childTag.AddCssClass(attribute.Value.ToString());
                                break;
                            case "InnerText":
                                childTag.SetInnerText(attribute.Value.ToString());
                                break;
                            default:
                                childTag.MergeAttribute(attribute.Key, attribute.Value.ToString());
                                break;
                        }
                    }
                    childTag.ToString(TagRenderMode.SelfClosing);
                    if (childTag != null) anchorTag.InnerHtml += childTag.ToString();
                }                    
            }
            return MvcHtmlString.Create(anchorTag.ToString(TagRenderMode.Normal));
        }
        else
        {
            return htmlHelper.ActionLink(linkText, actionName, controllerName, routeValues, htmlAttributesDictionary);
        }
    }

1
มันยอดเยี่ยมมากที่คุณได้รับแรงบันดาลใจและมีความสามารถในการทำสิ่งนี้ อย่างไรก็ตามฉันดูงบ foreach ที่ซ้อนกันและต้องการเรียกใช้ มันก็ไม่สามารถบำรุงรักษาได้โดยนักพัฒนาส่วนใหญ่ หากเป็นชุดสวยในวิธีการขยายประเภทกล่องดำหินอาจเป็นไปได้ แต่มันมีกลิ่นรหัส ไม่ใช่เรื่องง่ายเลยสำหรับบางสิ่งที่ค่อนข้างง่าย ขอบคุณสำหรับความพยายามของคุณ
Tom Stickel

ฉันเห็นด้วยอย่างมากกับการซ้อนกันสำหรับลูป เพื่อความรัดกุมมันอยู่ที่นั่น จากจุดเพิ่มประสิทธิภาพที่เหมาะสมใช่ว่าการซ้อนวนสำหรับลูปควรอยู่ในวิธีการส่วนตัวของตัวเองและจำเป็นต้องมีการยืนยันพารามิเตอร์รหัสจะต้องมีการป้องกันที่มากขึ้น ฯลฯ
william-kid

0

มันง่ายมาก

หากคุณต้องการมีไอคอน glyphicon จากนั้น "Wish List"

<span class="glyphicon-heart"></span> @Html.ActionLink("Wish List (0)", "Index", "Home")

0

โซลูชันของฉันใช้ส่วนประกอบบู๊ตสแตรป:

<a class="btn btn-primary" href="@Url.Action("resetpassword", "Account")">
    <span class="glyphicon glyphicon-user"></span> Reset Password
</a>

0

โปรดลองรหัสด้านล่างที่อาจช่วยคุณ

 @Html.ActionLink(" SignIn", "Login", "Account", routeValues: null, htmlAttributes: new {  id = "loginLink" ,**@class="glyphicon glyphicon-log-in"** }) 

ง่ายๆเพียงเพิ่ม @ class และจากนั้นชั้นเรียน css ที่แท้จริงช่วยฉันแก้ปัญหาของฉัน
Ahsanul
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.