2013-03-04 28 views
1

我用派生類,接口和視圖模型來修飾,但我一直無法創建我所需要的。是否有將多個模型的顯示標準化爲單個視圖的設計模式?

假設我們正在構建一個CMS有如下型號:

ArticleItem

  • 標題

  • 摘要

  • 內容

NewsItem

  • 頭銜

  • PublishDate

  • 摘要

  • 內容

EventItem

  • EVENTTITLE

  • 起始日期

  • 結束日期

  • 內容

我尋找一種方法來將這些顯示標準化爲一種格式/視圖(例如,所以我們可以將它們全部顯示在同一個RSS提要中)。標準化的觀點可能被稱爲HTMLItem,並有3個領域:

  • 標題

  • 摘要

  • 內容

ArticleItem將直接轉換爲HTMLItem,這很簡單。

對於NewsItem我想加盟PublishDate和內容的前100個字符創建HTMLItem的彙總字段。

對於EventItem我想起始日期日期和結束日期相結合,創造HTMLItem的彙總字段。

最終,我正在尋找最簡單,最有效的方法,能夠將3個模型傳遞到設計爲顯示HTMLItem的單個視圖中。到目前爲止,我的最好成績是爲每個模型創建一個「轉換器」類,但我不禁感覺有更好的方法來做到這一點。

任何經驗,專業知識和建議將不勝感激!

回答

1

做一個視圖模型與標化性能和構造每個專業類:

public class HtmlItemViewModel { 
    //Properties 
    public string Title {get; set;} 
    public string Summary {get; set;} 
    public string Content {get; set;} 

    //Constructor inside HtmlItemViewModel for each one of the specialized classes: 
    public HtmlItemViewModel(ArticleItem item) 
    { 
     this.Title = item.Title; 
     this.Summary = item.Summary; 
     this.Content = item.Content; 
    } 

    public HtmlItemViewModel(NewsItem item) 
    { 
     this.Title = item.Headline; 
     this.Summary = String.Format("{0} - {1}", item.PublishDate, item.Summary.Substring(0,1000)); 
     this.Content = item.Content; 
    } 

    public HtmlItemViewModel(EventItem item) 
    { 
     this.Title = item.EventTitle; 
     this.Summary = String.Format("{0} - {1}", item.StartDate, item.EndDate); 
     this.Content = item.Content; 
    } 
} 

然後,在您使用您的RSS提要的方法中,每個實體簡單地傳遞給構造上的每個單獨的查詢。像這樣:

//Example controller 
public class RssController : Controller { 
    public ActionResult GetRssFeed(){ 
     //Assuming you have a service for each item type 
     var articleList = ArticleService.GetArticles().Select(s => new HtmlItemViewModel(s)); 
     var newsItemList = NewsItemService.GetNewsItems().Select(s => new HtmlItemViewModel(s)); 
     var eventItemList = EventItemService.GetEvents().Select(s => new HtmlItemViewModel(s)); 

     articleList.AddRange(newsItemList); 
     articleList.AddRange(eventItemList); 

     return articleList; 
    } 
} 
+0

謝謝你,我認爲這是我要採取的方法。每個班級的構造函數都會吸引我的內心小玩意兒。 – 2013-03-05 10:29:38

+0

@四十二:關於映射選項和數據註釋,您的回答也非常有幫助。實際上,我沒有意識到它們可以用在視圖模型上: - $非常感謝你們倆 – 2013-03-05 10:35:28

0

您可以使用Viewmodel模式在您的項目

模型和的ViewModels是不同的。不要將ViewModel與MVVM模式混淆。

使用視圖模型可以使模型和 視圖之間的交互更加簡單。模型有時會在複雜的具有其它 模型對象作爲成員,這可能會對模型對象爲 成員等。

通過使用視圖模型,你必須簡化什麼看法 涉及一個好辦法。這也將濾除在intellisense中看到的東西,所以如果你有不同的人開發模型 比那些在視圖上工作的人,創建一個簡單的視圖模型可以使 更容易處理用戶界面。

+0

只是爲了澄清(作爲c#noob),這將是最好的實現與某種映射系統,因爲它是自己的類或在控制器? – 2013-03-04 12:00:27

0

對此的簡單和最常見的解決方案是創建一個複合視圖模型類。這可以是一個組合類(包含對您的域模型的引用),也可以是一個扁平化類,分別引用每個類的屬性。

所以,你可以這樣做:

public class HtmlItemViewModel 
{ 
    public ArticleItem ArticleItem {get; set;} 
    public NewsItem NewsItem {get; set;} 
    public EventItem EventItem {get; set;} 
} 

或者這樣:

public class HtmlItemViewModel 
{ 
    //Article Item Properties 
    public string ArticleTitle {get; set;} 
    public string ArticleContent {get; set;} 
    public string ArticleSummary {get; set;} 
    //News Item Properties 
    public string Headline {get; set;} 
    public DateTime PublishDate {get; set;} 
    public string NewsItemSummary {get; set;} 
    public string NewsItemContent {get; set;} 
    //Event Item Properties 
    public string EventTitle {get; set;}  
    public DateTime StartDate {get; set;}  
    public DateTime EndDate {get; set;} 
    public string EventContent {get; set;} 
} 

然後,你選擇構建視圖模型無論怎樣,你會映射到域模型視圖模型屬性(s)在控制器中。爲此,您可以映射手動

HtmlItemViewModel.ArticleTitle = ArticleItem.ArticleTitle; 
//and so on... 

或者你也可以使用第三方工具,如AutoMapper

我傾向於在大多數情況下展平視圖模式,因爲它可以讓我只送我需要的數據,不多也不少。它還允許我將數據註釋用於視圖模型上的輸入驗證,而不是域模型。

相關問題