【问题标题】:ASP.NET MVC HtmlHelper extensions for YUI controls (Yahoo User Interfaces)?用于 YUI 控件(雅虎用户界面)的 ASP.NET MVC HtmlHelper 扩展?
【发布时间】:2010-10-03 11:55:36
【问题描述】:

有没有人为 MVC 写过任何 HTMLHelper classes 来帮助 Yahoo's User Interface Library

例如,我编写了一个辅助方法来将“菜单模型”转换为支持Yahoo Menu Control 所需的 HTML 标记。 MVC 模式在这里工作得很好,因为很明显,如果我选择切换到不同的菜单实现,我可以只编写一个新的帮助程序而不接触模型。

此代码适用于我,但尚未经过全面测试,欢迎您使用。

首先,我们需要菜单模型本身的简单数据结构。您可以使用正常的 MVC 约定将其添加到您的页面模型中。例如,我通过ViewData.Model.MainMenu.MenuOptions 从我的视图中访问菜单项列表。

public class MenuItem

{
    public string Text { get; set; }
    public string Description { get; set; }
    public string RouteURL { get; set; }
    public bool SeparatorBefore { get; set; }

    public List<MenuItem> MenuItems { get; set; }
}

扩展方法。放入您的视图可访问的命名空间。

public static class YUIExtensions
    {
        public static string RenderMenu(this HtmlHelper html, string id, List<MenuItem> menuItems)
        {
            // <div id="mnuTopNav" class="yuimenubar yuimenubarnav">
            //    <div class="bd">
            //        <ul class="first-of-type">

            //            <li class="yuimenubaritem first-of-type"><a class="yuimenubaritemlabel" href="#store">Store</a></li>

            //            <li class="yuimenubaritem"><a class="yuimenubaritemlabel" href="#products">Products</a>

            //                <div id="communication" class="yuimenu">
            //                    <div class="bd">
            //                        <ul>
            //                            <li class="yuimenuitem"><a class="yuimenuitemlabel" href="http://360.yahoo.com">360&#176;</a></li>
            //                            <li class="yuimenuitem"><a class="yuimenuitemlabel" href="http://mobile.yahoo.com">Mobile</a></li>
            //                            <li class="yuimenuitem"><a class="yuimenuitemlabel" href="http://www.flickr.com">Flickr Photo Sharing</a></li>
            //                        </ul>
            //                    </div>
            //                </div>     
            //            </li>

            //        </ul>            
            //    </div>
            //</div>   

            int menuId = 0;
            HtmlGenericControl menuControl = CreateControl(html, id, 0, ref menuId, menuItems);

            // render to string
            StringWriter sw = new StringWriter();
            HtmlTextWriter tw = new HtmlTextWriter(sw);
            tw.Indent = 1;
            menuControl.RenderControl(tw);
            return sw.ToString();
        }

        private static HtmlGenericControl CreateControl(HtmlHelper html, string id, int level, ref int menuId, List<MenuItem> currentItems)
        {
            var menu = new HtmlGenericControl("div");
            menu.Attributes["class"] = (level == 0) ? "yuimenubar yuimenubarnav" : "yuimenu";
            menu.Attributes["id"] = id;

            var div_bd = new HtmlGenericControl("div");
            menu.Controls.Add(div_bd);
            div_bd.Attributes["class"] = "bd";

            HtmlGenericControl ul = null;

            int i = 0;
            foreach (var menuItem in currentItems)
            {
                if (ul == null || menuItem.SeparatorBefore)
                {
                    ul = new HtmlGenericControl("ul");
                    div_bd.Controls.Add(ul);

                    if (i == 0)
                    {
                        ul.Attributes["class"] = "first-of-type";
                    }
                }

                var menuItem_li = new HtmlGenericControl("li");
                menuItem_li.Attributes["class"] = (level == 0) ? "yuimenubaritem" : "yuimenuitem";
                if (i == 0)
                {
                    menuItem_li.Attributes["class"] += " first-of-type";
                }
                ul.Controls.Add(menuItem_li);

                var href = new HtmlGenericControl("a");
                href.Attributes["class"] = (level == 0) ? "yuimenubaritemlabel" : "yuimenuitemlabel";
                href.Attributes["href"] = menuItem.RouteURL;
                href.InnerHtml = menuItem.Text;
                menuItem_li.Controls.Add(href);

                if (menuItem.MenuItems != null && menuItem.MenuItems.Count > 0)
                {
                    menuItem_li.Controls.Add(CreateControl(html, id + "_" + (menuId++), level + 1, ref menuId, menuItem.MenuItems));
                }
                i++;
            }

            return menu;
        }
    }

将此代码粘贴到您要在视图中生成菜单的位置(我在母版页中有此代码):

<%= Html.RenderMenu("mnuTopNav", ViewData.Model.MainMenu.MenuOptions) %>

如果你很懒,或者不了解 YUI,你的 &lt;HEAD&gt; 中也需要这个

<!-- Combo-handled YUI CSS files: -->
<link rel="stylesheet" type="text/css" href="http://yui.yahooapis.com/combo?2.6.0/build/menu/assets/skins/sam/menu.css">
<!-- Combo-handled YUI JS files: -->
<script type="text/javascript" src="http://yui.yahooapis.com/combo?2.6.0/build/yahoo-dom-event/yahoo-dom-event.js&2.6.0/build/container/container_core-min.js&2.6.0/build/menu/menu-min.js"></script>

这目前会为 top nav style navigation bar 生成标记 - 但可以轻松修改。

我希望其他人对其他一些控件也做同样的事情。

似乎是一个开源项目的好人选 - 但我没有时间开始。

欢迎提出实施建议!

【问题讨论】:

    标签: asp.net-mvc yui html-helper


    【解决方案1】:

    昨晚我对此进行了一些思考,想知道这里是否有更多机会使用 YUI 或您想要的任何其他 Javascript/HTML 小部件来制作通用 HTMLHelper。

    例如,如果有一个用于 IMenu 的接口和一个用于 ITextBox、ICheckBox、IRichTextEditor、ICarousel 等的接口,就像您的 MenuItem 类一样,那么您可以对每个接口都有一个 YUI 实现,一个用于 JQuery , 一个用于 MooTools 或一个仅用于 HTML/CSS。

    引发这种情况的部分原因是这样的文章:http://designingwebinterfaces.com/essential_controls 正在将 Web 上的 UI 控件用于富 Web 应用程序。

    这些接口将包含所有乍一看很明显的基本内容:Id、Name、Value、List、Style、OnChange、OnClick 等,以及 ValidationRegex、HelpText 等不太明显的内容。

    这将使您拥有一个将模型对象或模型属性转换为 ITextBox 的层,而不必担心接口的哪个实现将实际处理它。如果出现更好/更快/更酷的新实现,您也可以轻松切换到新的实现。

    如果您将 ValidationRegex 之类的东西提供给准系统 HTML 实现并且它无法处理它,您将不得不处理会发生什么,但我认为这是一条值得思考的路径。我还认为,通过继承或重新实现它,将它与现有的 HTMLHelper 命名空间分开实现可能更有意义,但在提出解决方案的这种早期想法阶段,我经常犯错。

    YUIAsp.NET 的东西很有趣,但比 ASP.NET MVC 和 Fubu MVC 最近的发展方向更面向 WebForms 和用户控件。

    我对这个想法进行了一些修改,并对其中的可能性非常感兴趣。

    【讨论】:

    • 我使用的都不是 YUI 中的 ASP.NET。它完全是 javascript。当你完成修补时告诉我:)
    【解决方案2】:

    西蒙,

    我不确定这对 MVC 问题是否有帮助,但有一个很好的开源项目旨在简化在 .NET 中使用 YUI:

    http://www.yuiasp.net/

    菜单是它们包含的控件之一。

    至少,如果您的工作为已经存在的东西增加了新的维度,那么这可能是一个您可以回馈的项目。

    -埃里克

    【讨论】:

    • 谢谢。我会检查一下。肯定有一些工作可以分享——他们很可能已经在做这件事了
    猜你喜欢
    • 2023-03-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-01-15
    • 1970-01-01
    相关资源
    最近更新 更多