2014-03-31 68 views
1

我正在使用MVC4的MvcSiteMapProvider(v4.6.1)來處理麪包屑和菜單。我已經完成了關於安裝,配置和使用@Html.MvcSiteMap().Menu()的100個級別的教程。使用MvcSiteMapProvider顯示節點級別的一部分

我現在想要一個顯示頂級部分的菜單。目前,我的頂級節點包括Home,Profile,Login,Thing 1,Thing 2和Thing 3.藉助this SOf answer,我製作了一個菜單,以水平行顯示所有這些項目。我還確定,一旦系統包含授權,無法訪問Thing 3的用戶將無法在其菜單上看到該內容。

我想要的只是顯示一些項目:家庭和登錄必須在麪包屑中顯示,但不能在菜單中顯示。請注意,它們在當前站點地圖中不是連續的。

你們都建議了哪些建議?

我目前的觀點,從鏈接答案採取批發:

@model MvcSiteMapProvider.Web.Html.Models.MenuHelperModel 
@using MvcSiteMapProvider.Web.Html.Models 

<div class="nav navbar-nav navbar-left"> 
    <ul class="nav navbar-nav"> 
     @foreach (var node in Model.Nodes) { 
      <li>@Html.DisplayFor(m => node)</li> 
     } 
    </ul> 
</div> 

我現在從我的菜單視圖中調用這個觀點:

@Html.MvcSiteMap().Menu("MenuHelper", 0, true, false, 1) 

我當然可以,做一個新的菜單幫手過濾出我不想展示的那些。

編輯:Mvc.sitemap:

<mvcSiteMapNode title="Home" controller="Home" action="Index" visibility="MainMenu,!*"> 
    <mvcSiteMapNode title="About" controller="Home" action="About"/> 
    <mvcSiteMapNode title="Profile" controller="Home" action="UpdateProfile" visibility="MainMenu,!*"/> 
    <mvcSiteMapNode title="Login" controller="SGAccount" action="Login"> 
     <mvcSiteMapNode title="Register" controller="SGAccount" action="Register"> 
     </mvcSiteMapNode> 
    </mvcSiteMapNode> 
    <mvcSiteMapNode title="Thing1" controller="Thing1" action="Index" visibility="MainMenu,!*"> 
     <mvcSiteMapNode title="Thing1-action1" controller="Thing1" action="action1" visibility="RoleMenu,!*"/> 
     <mvcSiteMapNode title="Thing1-action2" controller="Thing1" action="action2" visibility="RoleMenu,!*"/> 
    </mvcSiteMapNode> 
    <mvcSiteMapNode title="Thing2" controller="Thing2" action="Index" visibility="MainMenu,!*"> 
    </mvcSiteMapNode> 
    </mvcSiteMapNode> 

的MainMenu顯示主頁,關於,檔案,登錄,Thing1和Thing2。它不應該顯示所有這一切。

編輯2:使用結構映射爲外部DI,我加了這一行,但我不能肯定它是正確的:

x.For<ISiteMapNodeVisibilityProviderStrategy>().Use<SiteMapNodeVisibilityProviderStrategy>(); 

編輯3:我的麪包屑,@Html.MvcSiteMap().SiteMapPath(),停止工作。這也需要修復。

編輯4:我通過從web.config中刪除內部DI設置來解決前兩個編輯的問題。現在我回過頭來展示我想展示的內容。

回答

4

完成此操作的最佳方法是將named HTML helpers與ISiteMapNodeVisibilityProvider結合使用。在框中有一個FilteredSiteMapNodeVisibilityProvider,通過給每個菜單命名,可以用來在某些Menu實例上顯示一個節點。

1)設置VisibilityAffectsDescendants爲false,默認可視性提供商FilteredSiteMapNodeVisibilityProvider

<appSettings> 
    <add key="MvcSiteMapProvider_VisibilityAffectsDescendants" value="false"/> 
    <add key="MvcSiteMapProvider_DefaultSiteMapNodeVisibiltyProvider" value="MvcSiteMapProvider.FilteredSiteMapNodeVisibilityProvider, MvcSiteMapProvider"/> 
</appSettings> 

對於外部DI,這些設置需要由DI容器提供。這裏是你如何在StructureMap中做到這一點。

// Near the top of the DI module 
// (this setting is provided to the constructor of SiteMapBuilderSet) 
bool visibilityAffectsDescendants = false; 

// Visibility Providers 
this.For<ISiteMapNodeVisibilityProviderStrategy>().Use<SiteMapNodeVisibilityProviderStrategy>() 
    .Ctor<string>("defaultProviderName").Is("MvcSiteMapProvider.FilteredSiteMapNodeVisibilityProvider, MvcSiteMapProvider"); 

2)給每個菜單的名稱通過sourceMetaData參數

@Html.MvcSiteMap().Menu(new { name = "TopMenu" }) 
@Html.MvcSiteMap().Menu(new { name = "SideMenu" }) 
@Html.MvcSiteMap().Menu(new { name = "BottomMenu" }) 

3)設置每個節點的可見性屬性所描述here。請記住,您也可以通過HTML助手類型進行過濾。

<mvcSiteMapNode title="Home" controller="Home" action="Index" visibility="TopMenu,BottomMenu,SiteMapPathHelper,!*"> 
    <mvcSiteMapNode title="About" controller="Home" action="About" visibility="SideMenu,BottomMenu,SiteMapPathHelper,!*"/> 
    <mvcSiteMapNode title="Contact" controller="Home" action="Contact" visibility="TopMenu,SiteMapPathHelper,!*"/> 
</mvcSiteMapNode> 

如果您有更復雜的可見性規則,您甚至可以implement your own ISiteMapNodeVisibilityProvider

請注意,能見度也受security trimming影響,但安全修剪總是隱藏隱藏節點的所有後代節點。啓用安全修整後,根據可見性提供者的不同,每個節點都必須可以通過安全方式進行訪問,以便在UI上可見。

如果沒有與當前頁面匹配的節點,基於層的麪包屑痕跡和菜單也會自動隱藏。閱讀How to Make MvcSiteMapProvider Remember a User's Position深入瞭解匹配行爲。這僅適用於具有「id」或其他自定義參數的路線。

+0

這應該有所幫助。我的規則很簡單 - 菜單X應該對每個人都可見,菜單Y應該基於角色可見。而且我已經知道MvcSiteMapProvider處理「基於角色」就好了。 –

+0

這沒有按預期工作。讓我發佈我的站點地圖文件。 –

+0

我更新並更正了我的答案,以包含外部DI的示例。確保您將VisibilityAffectsDescendants設置爲false(我的上一個示例顯示爲true),否則您的菜單將始終隱藏不可見節點的後代節點。另請參閱更新後的項目3,始終顯示麪包屑路徑中的項目。 – NightOwl888

相關問題